Skip to main content
The Vault Hardware Security Module (HSM) auto-unseal and Seal Wrap features require Vault Enterprise with the Governance & Policy Module.
To configure the Futurex PKCS #11 library with Vault, perform the following tasks:
  1. Download and install Vault.
  2. Configure Vault.
  3. Use Vault.
  4. Enable the Seal Wrap feature.
  5. Test the Seal Wrap feature.
  6. Enable and test the Entropy Augmentation feature.
The following sections describe how to perform these tasks.

Download Vault

Download precompiled Vault binaries at https://releases.hashicorp.com/vault/. To download Vault Enterprise binaries, follow the instructions HashiCorp provides Vault customers. This integration requires the Enterprise HSM binary, which is available for testing: https://releases.hashicorp.com/vault/1.7.2+ent.hsm/

Install Vault

Perform the following steps to install Vault:
1
Run the following command to unzip the downloaded package and then move the vault binary to /usr/local/bin:
Shell
unzip vault_${VAULT_VERSION}+ent.hsm_linux_amd64.zip
2
Run the following command to set the owner of the Vault binary:
Shell
sudo chown root:root vault
3
Check that vault is available on the system path.
Shell
sudo mv vault /usr/local/bin/
4
Run the following command to verify the Vault version:
Shell
vault --version
5
The vault command features opt-in autocompletion for flags, subcommands, and arguments (where supported).Install autocompletion using the following command:
Shell
vault -autocomplete-install
6
Run the following command to enable autocompletion:
Shell
complete -C /usr/local/bin/vault vault
7
Run the following command to configure Vault to use the mlock syscall without running the process as root. This operation prevents the system from swapping memory to disk.
Shell
sudo setcap cap_ipc_lock=+ep /usr/local/bin/vault
8
Run the following command to create a unique, non-privileged system user to run vault:
Shell
sudo useradd --system --home /etc/vault.d --shell /bin/bash vault

Configure Vault

To configure Vault, perform the following tasks:
  1. Configure systemd.
  2. Configure Vault settings.
  3. Configure HSM Auto-unseal and Entropy Augmentation

Configure systemd

Systemd uses documented sane defaults (www.freedesktop.org/software/systemd/man/systemd.directives.html), so you need to set only non-default values in the configuration file.
1
Run the following command to create a Vault service file at /etc/systemd/system/vault.service:
Shell
sudo touch /etc/systemd/system/vault.service
2
Add the following configuration to vault.service:
None
[Unit]
Description="HashiCorp Vault - A tool for managing secrets"
Documentation=https://www.vaultproject.io/docs/
Requires=network-online.target
After=network-online.target
ConditionFileNotEmpty=/etc/vault.d/vault.hcl
StartLimitIntervalSec=60
StartLimitBurst=3

[Service]
User=vault
Group=vault
ProtectSystem=full
ProtectHome=read-only
PrivateTmp=yes
PrivateDevices=yes
SecureBits=keep-caps
AmbientCapabilities=CAP_IPC_LOCK
Capabilities=CAP_IPC_LOCK+ep
CapabilityBoundingSet=CAP_SYSLOG CAP_IPC_LOCK
NoNewPrivileges=yes
ExecStart=/usr/local/bin/vault server -config=/etc/vault.d/vault.hcl
ExecReload=/bin/kill --signal HUP $MAINPID
KillMode=process
KillSignal=SIGINT
Restart=on-failure
RestartSec=5
TimeoutStopSec=30
StartLimitInterval=60
StartLimitIntervalSec=60
StartLimitBurst=3
LimitNOFILE=65536
LimitMEMLOCK=infinity

[Install]
WantedBy=multi-user.target

Configure Vault settings

Vault uses documented sane defaults, so you need to set only non-default values in the configuration file.
1
Run the following command to create /etc/vault.d directory:
Shell
sudo mkdir --parents /etc/vault.d
2
Run the following command to create a Vault configuration file, vault.hcl:
Shell
sudo touch /etc/vault.d/vault.hcl
3
Run the following command to set the ownership of the /etc/vault.d directory:
Shell
sudo chown --recursive vault:vault /etc/vault.d
4
Run the following command to set the file permissions:
Shell
sudo chmod 640 /etc/vault.d/vault.hcl

Configure HSM Auto-unseal and Entropy Augmentation

When you start a Vault server, it normally starts in a sealed state where you must have a quorum of existing unseal keys to unseal it. By integrating Vault with the KMES Series 3, a trusted HSM key provider can automatically unseal the Vault server. To integrate the Vault Enterprise server with a KMES Series 3, the configuration file must define the PKCS11 seal stanza and provide the necessary connection information, as shown in the following example: Example: vault.hcl
None
# Provide your Futurex HSM connection information
seal "pkcs11" {
  lib = "/usr/local/bin/fxpkcs11/x64/OpenSSL-1.1.x/libfxpkcs11.so"
  slot = "0"
  key_label = "hsm_demo"
  hmac_key_label = "hsm_hmac_demo"
  generate_key = "true"
}

# Add the entropy stanza
entropy "seal" {
  mode = "augmentation"
}

# Configure the storage backend for Vault
storage "file" {
  path = "/tmp/vault"
}

# Addresses and ports on which Vault will respond to requests
listener "tcp" {
  address          = "0.0.0.0:8200"
  tls_disable      = "true"
}

ui = true
disable_mlock = true
This guide sets the storage backend to the local file system (/tmp/vault) to make the verification step easy.
The example configuration defines the following in its seal stanza:
ParameterDescription
libThe path to the PKCS #11 library on the machine where Vault Enterprise is installed.
slotThe slot number to use. Set this value to 0 because the FXPKCS11 config file sets the slot to 01 by default.
key_labelThe label of the key to use.
hmac_key_labelThe label of the key to use for HMACing
generate_keyIf no existing key with the label specified by key_label exists at Vault initialization, Vault generates a key.
For this integration, set the generate\key parameter to true so that Vault automatically creates the encryption keys that it uses for the Seal Wrap functionality on the KMES. The values set for the key\label and hmac\key\label parameters correspond with the special key label defines that youneed to set in the <CONFIG> section of the fxpkcs11.cfg file).

Use Vault

To get started using Vault, perform the following tasks:
  1. Start the Vault server.
  2. Initialize Vault.
  3. Access the Vault UI.

Start the Vault server

Perform the following steps to start the Vault server:
1
Log in with the vault user.
2
Run the following command to set the PKCS #11 PIN to log in. Use the password of the user you created on the KMES and defined in the fxpkcs11.cfg file.
Shell
export VAULT_HSM_PIN='safest'
You can also set the PKCS #11 PIN in the Vault configuration file ( vault.hcl) with the pin parameter, but we do not recommend that method in a production setting. As a best practice, specify the pin with the VAULT\HSM\PIN environment variable, as shown here, to prevent password exposure if the config file is compromised or stored in an insecure location. If you set it through the environment variable, Vault obfuscates the environment variable after reading it. One caveat: You must reset the VAULT\HSM\PIN environment variable when Vault restarts.
3
Run the following command to start the Vault server:
Shell
vault server -config=/etc/vault.d/vault.hcl
If the command succeeds, expect output similar to the following example:
None
==> Vault server configuration:
     HSM PKCS#11 Version: 2.20
             HSM Library: FxPKCS11
     HSM Library Version: 4.23
     HSM Manufacturer ID: Futurex
                HSM Type: pkcs11
                     Cgo: enabled
              Go Version: go1.14.4
              Listener 1: tcp (addr: "0.0.0.0:8200", cluster address: "0.0.0.0:8201", maxrequestduration: "1m30s", maxrequestsize: "33554432", tls: "disabled")
               Log Level: info
                   Mlock: supported: true, enabled: false
           Recovery Mode: false
                 Storage: file
                 Version: Vault v1.5.0+ent.hsm
==> Vault server started! Log data will stream in below:
4
Open a new terminal window for later steps and leave this terminal running where you started the Vault server.

Initialize Vault

Perform the following steps to initialize Vault:
1
In the new terminal, run the following command to set the VAULT_ADDR environment variable
Shell
export VAULT_ADDR='http://0.0.0.0:8200'
2
Run the following command to check the Vault status:
Shell
vault status
The output should be similar to the following example:
None
Key                      Value
---                      -----
Recovery Seal Type       pkcs11
Initialized              false
Sealed                   true
Total Recovery Shares    0
Threshold                0
Unseal Progress          0/0
Unseal Nonce             n/a
Version                  n/a
HA Enabled               false
3
Run the following command to initialize Vault:
Shell
vault operator init -recovery-shares=1 -recovery-threshold=1
The output should be similar to the following example:
None
Recovery Key 1: E22HrXUFAyQy0PVUy+renVPXoLZ0bSRjWAsTZ64rE24=

Initial Root Token: s.mvX8cihrFqMWEiM9YFnlw9E1

Success! Vault is initialized

Recovery key initialized with 1 key shares and a key threshold of 1. Please
securely distribute the key shares printed above.
4
Run the following command to set the VAULT_TOKEN environment variable value to the generated Initial Root Token value displayed in the terminal output:
Shell
export VAULT_TOKEN="s.mvX8cihrFqMWEiM9YFnlw9E1"
To interact with Vault, you must provide a valid token.

Access the Vault UI

Perform the following steps to access the Vault UI:
1
Go to http://localhost:8200 in a web browser.
2
Copy and paste the Initial Root Token output from the Vault initialization command into the Token field, and select [ Sign in ].
If the login succeeds, the Vault UI homepage displays.

Enable the Seal Wrap feature

You can enable Seal Wrap by using the following methods:
  • CLI command
  • Web UI
Perform one of the methods described in the following sections.

Method 1: CLI command

Perform the following steps to execute the CLI command method:
1
To compare seal-wrapped data against unwrapped data, enable key/value v1 secrets engine at two different paths: kv-unwrapped and kv-seal-wrapped.Run the following command to enable k/v v1 without seal wrap at kv-unwrapped:
Shell
vault secrets enable -path=kv-unwrapped kv
Run the following command to enable k/v v1 with seal wrap by using the -seal-wrap flag when you enable the KV workflow:
Shell
vault secrets enable -path=kv-seal-wrapped -seal-wrap kv
To enable seal wrap, pass the -seal-wrap flag when you enable a secrets engine
2
Run the following command to list the enabled secrets engines with details:
Shell
vault secrets list -detailed
If the command succeeds, the output is similar the the following example:
None
Path                Plugin       Accessor              ...    Seal Wrap    ...
----                ------       --------                     -----------  ...
cubbyhole/          cubbyhole    cubbyholeb36dd7e1    ...    false        ...
identity/           identity     identityb5650a96     ...    false        ...
kv-seal-wrapped/    kv           kvfe02767b           ...    true         ...
kv-unwrapped/       kv           kv36d321c6           ...    false        ...
...
Notice that the Seal Wrap parameter value is true for kv-seal-wrapped/.

Method 2: Web UI

Perform the following steps to execute the Web UI method:
1
Open a web browser and launch the Vault UI (for example, http://127.0.0.1:8200/ui) and then log in.
2
Select Enable new engine.
3
Select KV from the list, and then select [ Next ].
4
Enter kv-unwrapped in the path field and select Version 1 for KV version.
5
Return to the Secrets Engines page and select [ Enable Engine ].
6
Select KV from the list, and then select [ Next ].
7
Enter kv-seal-wrapped in the path field. Select Version 1 for KV version.
8
Select [ Method Options ] to expand, and select the check box for Seal Wrap.
9
Select [ Enable Engine ].

Test the Seal Wrap feature

You can test Seal Wrap and view encrypted secrets by using one of the following methods:
  • CLI command
  • Web UI
Perform one of the methods described in the following sections.

Method 1: CLI command

Perform the following steps to execute the CLI command method:
1
Run the following command to write a secret at kv-unwrapped/unwrapped for testing:
Shell
vault kv put kv-unwrapped/unwrapped password="my-long-password"
2
Run the following command to read the path to verify:
Shell
vault kv get kv-unwrapped/unwrapped
If the command succeeds, the output is similar the the following example:
None
====== Data ======
Key         Value
---         -----
password    my-long-password
3
Run the following command to write the same secret at kv-seal-wrapped/wrapped for testing:
Shell
vault kv put kv-seal-wrapped/wrapped password="my-long-password"
4
Run the following command to read the path to verify:
Shell
vault kv get kv-seal-wrapped/wrapped
If the command succeeds, the output is similar the the following example:
None
====== Data ======
Key         Value
---         -----
password    my-long-password
Use a valid token to write and read secrets the same way, regardless of the seal wrap.

View the encrypted secrets

Remember that you configured the Vault server to use the local file system (/tmp/vault) as its storage backend, as shown in the following example:
None
# Configure the storage backend for Vault
storage "file" {
  path = "/tmp/vault"
}
Perform the following steps to view the encrypted secrets:
1
SSH into the machine where the Vault server is running, and check the stored values in the /tmp/vault directory:
Shell
cd /tmp/vault/logical
The /tmp/vault/logical directory has two sub-directories. One maps to kv-unwrapped/ and another maps to kv-seal-wrapped/ although you cannot tell by the folder names.
2
View the secret at rest. One of the directories maps to kv-unwrapped/unwrapped.

Example of viewing encrypted secrets

The following example demonstrates viewing encrypted secrets:
1
Go the first directory:
Shell
cd 2da357cd-55f2-7eed-c46e-c477b70bed18
2
Run the following command to view its content. The password value is encrypted.
Shell
cat _unwrapped

{"Value":"AAAAAQICk547prhuhMiBXLq2lx8ZkMpSB3p+GKHAwuMhKrZGSeqsFevMS6YoqTVlbvpU9B4zWPZ2HA
SeNZ3YMw=="}
3
Go to the other directory that maps to kv-seal-wrapped/wrapped. Then, run the following command to view its content. The password value is encrypted.
4
Shell
    cat _wrapped

    {"Value":"ClBAg9oN7zBBaDBZcsilDAyGkL7soPe7vBA5+ADADuyzo8GuHZHb9UFN2nF1h0OpKEgCIkG3JNHcXt
    tZqCi6szcuNBgF3pwhWGwB4FREM3b5CRIQYK7239Q92gRGrcBBeZD6ghogEtSBDmZJBahk7n4lIYF3X4iBqmwZgH
    Vo4lzWur7rzncgASofCIIhENEEGghoc21fZGVtbyINaHNtX2htYWNfZGVtb3M="}
Secrets are encrypted, but the seal-wrapped value is significantly longer even though both values are the same: my-long-password.

Method 2: Web UI

Perform the following steps to execute the Web UI method:
1
Select kv-unwrapped and select [ Create secret ].
2
Enter unwrapped in the Path for this secret field. Use password in the secret key field and my-longpassword in the value field.
3
Select [ Save ].
4
Repeat the same step for kv-seal-wrapped to write the same secret at the kv-seal-wrapped/wrapped path.
5
Select [ Save ].
You can write and read secrets the same way regardless of the seal wrap by using a valid token.

View the encrypted secrets

Remember that you configured the Vault server to use the local file system (/tmp/vault) as its storage backend, as shown in the following example:
None
# Configure the storage backend for Vault
storage "file" {
  path = "/tmp/vault"
}
1
SSH into the machine where the Vault server is running, and check the stored values in the /tmp/vault directory.
Shell
cd /tmp/vault/logical
The /tmp/vault/logical directory has two sub-directories. One maps to kv-unwrapped/ and another maps to kv-seal-wrapped/ although you cannot tell by the folder names.
2
View the secret at rest. One of the directories maps to kv-unwrapped/unwrapped.

Example of viewing encrypted secrets

The following example demonstrates viewing encrypted secrets:
1
Go to the first directory:
Shell
cd 2da357cd-55f2-7eed-c46e-c477b70bed18
2
Run the following command to view its content. The password value is encrypted.
Shell
cat _unwrapped

{"Value":"AAAAAQICk547prhuhMiBXLq2lx8ZkMpSB3p+GKHAwuMhKrZGSeqsFevMS6YoqTVlbvpU9B4zWPZ2HA
SeNZ3YMw=="}
3
Another directory maps to kv-seal-wrapped/wrapped.
Shell
cd ../5bcea44d-28a3-87af-393b-c6d398fe41d8
4
Run the following command to view its content. The password value is encrypted.
Shell
cat _wrapped

{"Value":"ClBAg9oN7zBBaDBZcsilDAyGkL7soPe7vBA5+ADADuyzo8GuHZHb9UFN2nF1h0OpKEgCIkG3JNHcXt
tZqCi6szcuNBgF3pwhWGwB4FREM3b5CRIQYK7239Q92gRGrcBBeZD6ghogEtSBDmZJBahk7n4lIYF3X4iBqmwZgH
Vo4lzWur7rzncgASofCIIhENEEGghoc21fZGVtbyINaHNtX2htYWNfZGVtb3M="}
Secrets are encrypted, but the seal-wrapped value is significantly longer even though both values are the same: my-long-password.

Enable and test the Entropy Augmentation feature

To leverage an external entropy source, you must set the external_entropy_access parameter to true when you enable a secrets engine or auth method. Perform the following steps to enable the KMES as the external entropy source on a transit secrets engine:
You must enable the Entropy Augmentation feature through the CLI because we do not support using the Web UI at this time.
1
Run the following command to enable the transit secrets engine with an external entropy source by using the -external-entropy-access flag:
Shell
vault secrets enable -external-entropy-access transit
2
Run the following command to list the enabled secrets engine with -detailed flag:
Shell
vault secrets list -detailed
Example output:
None
Path          Plugin       Accessor              ...  External Entropy Access  ...
----          ------       --------              ...  -----------------------  ...
cubbyhole/    cubbyhole    cubbyhole_a4084622    ...  false                    ...
identity/     identity     identity_b5738cb7     ...  false                    ...
sys/          system       system_a8b3552e       ...  false                    ...
transit/      transit      transit_88cd3066      ...  true                     ...
Notice that the External Entropy Access is set to true for transit/.
3
You can start using the transit secrets engine to encrypt your sensitive data which leverages the KMES as its external entropy source. Regardless, the user experience remains the same as before.

Example workflow

The following example demonstrates the workflow:
1
Run the following command to create a new encryption key named orders:
Shell
vault write -f transit/keys/orders
2
Run the following command to send a base64-encoded string for Vault to encrypt:
Shell
vault write transit/encrypt/orders plaintext=$(base64 <<< "4111 1111 1111 1111")

Key           Value
---           -----
ciphertext    vault:v1:AY3ZF2bwGfwZ9dJLSztCLdpPUHkfl/kwaQeRITvKgn74bGYyMI+n34w1CMO8aeg=
3
Run the following command to test and verify that you can decrypt the string:
Shell
vault write transit/decrypt/orders \
        ciphertext="vault:v1:AY3ZF2bwGfwZ9dJLSztCLdpPUHkfl/kwaQeRITvKgn74bGYyMI+n34w1CMO8aeg="
4
Run the following command to decode to get the original data:
Shell
base64 --decode <<< Y3JlZGl0LWNhcmQtbnVtYmVyCg==

credit-card-number
When you enable the external entropy access, you must set the connectivity to the KMES. If the KMES becomes unreachable for any reason, the transit secrets engine fails to generate new keys or rotate the existing keys, displaying an error similar to the following example
Shell
Error writing data to transit/encrypt/orders: Error making API request.

URL: PUT http://127.0.0.1:8200/v1/transit/encrypt/orders
Code: 400. Errors:

* error performing token check: failed to read entry: error initializing session
for decryption: error logging in to HSM: pkcs11: 0xE0: CKRTOKENNOT_PRESENT