Skip to main content

Deploying Machine ID on Linux (TPM)

This page explains how to deploy Machine ID on a Linux host, and use the secure identify of the onboard TPM 2.0 chip for authenticating with the Teleport cluster.

The tpm join method requires a valid Teleport Enterprise license to be installed on the cluster's Auth Service.

How it works

The tpm join method is a secure way for Bots and Agents to authenticate with the Teleport Auth Service without using any shared secrets. Instead of using a shared secret, the unique identity of the host's Trusted Platform Module (TPM) and public key cryptography is used to authenticate the host.

In environments where there is no other form of identity available to machines, e.g on-prem, this is the most secure method for joining. It avoids the need to distribute a shared secret as is needed for the token join method.

A Trusted Platform Module (TPM) is a secure, physical cryptoprocessor that is installed on a host. TPMs can store cryptographic material and perform a number of cryptographic operations, without exposing the cryptographic material to the operating system. Each TPM has a unique key pair burned-in known as the Endorsement Key (EK). This key does not change, even if the host operating system is reinstalled.

Some TPMs also contain an X.509 certificate for this key pair that is signed by the manufacturer's CA. This is known as the EK Certificate (EKCert). This certificate can be used by the TPM to prove to a third-party (who trusts the manufacturer's CA) that the TPM is genuine and abides by the TPM specification.

When using the tpm join method, you must first query the TPM's public key and then create a join token that explicitly allows this public key. To list information about the detected TPM, run the teleport tpm identify command.

If you have a large number of hosts, it may make sense to use automation tooling such as Ansible to query the TPMs across your fleet and then generate join tokens.

warning

The tpm join method is currently not compatible with FIPS 140-2.

Prerequisites

  • A running Teleport cluster version 17.0.0-dev or above. If you want to get started with Teleport, sign up for a free trial or set up a demo environment.

  • The tctl admin tool and tsh client tool.

    Visit Installation for instructions on downloading tctl and tsh.

  • To check that you can connect to your Teleport cluster, sign in with tsh login, then verify that you can run tctl commands using your current credentials. For example:
    $ tsh login --proxy=teleport.example.com --user=email@example.com
    $ tctl status
    # Cluster teleport.example.com
    # Version 17.0.0-dev
    # CA pin sha256:abdc1245efgh5678abdc1245efgh5678abdc1245efgh5678abdc1245efgh5678
    If you can connect to the cluster and run the tctl status command, you can use your current credentials to run subsequent tctl commands from your workstation. If you host your own Teleport cluster, you can also run tctl commands on the computer that hosts the Teleport Auth Service for full permissions.
  • A Linux host that you wish to install Machine ID onto, with a TPM2.0 installed.
  • A Linux user on that host that you wish Machine ID to run as. In the guide, we will use teleport for this.

Step 1/5. Install tbot

This step is completed on the Linux host.

First, tbot needs to be installed on the VM that you wish to use Machine ID on.

Download the appropriate Teleport package for your platform:

Install Teleport on your Linux server:

  1. Assign edition to one of the following, depending on your Teleport edition:

    EditionValue
    Teleport Enterprise Cloudcloud
    Teleport Enterprise (Self-Hosted)enterprise
    Teleport Community Editionoss
  2. Get the version of Teleport to install. If you have automatic agent updates enabled in your cluster, query the latest Teleport version that is compatible with the updater:

    $ TELEPORT_DOMAIN=example.teleport.com
    $ TELEPORT_VERSION="$(curl https://$TELEPORT_DOMAIN/v1/webapi/automaticupgrades/channel/default/version | sed 's/v//')"

    Otherwise, get the version of your Teleport cluster:

    $ TELEPORT_DOMAIN=example.teleport.com
    $ TELEPORT_VERSION="$(curl https://$TELEPORT_DOMAIN/v1/webapi/ping | jq -r '.server_version')"
  3. Install Teleport on your Linux server:

    $ curl https://cdn.teleport.dev/install-v15.4.11.sh | bash -s ${TELEPORT_VERSION} edition

    The installation script detects the package manager on your Linux server and uses it to install Teleport binaries. To customize your installation, learn about the Teleport package repositories in the installation guide.

Granting tbot access to the TPM device

If the user that will run tbot is not root, you will also need to configure Linux to allow the user to access the TPM device.

The simplest way to solve this is to check if your distro ships with the tss group and assign it the user. If that is not possible, or you are looking for a different solution, we recommend creating udev rules similar to the ones shipped by the TPM2 Software Stack.

Step 2/5. Create a Bot

Next, you need to create a Bot. A Bot is a Teleport identity for a machine or group of machines. Like users, bots have a set of roles and traits which define what they can access.

Create bot.yaml:

kind: bot
version: v1
metadata:
# name is a unique identifier for the Bot in the cluster.
name: example
spec:
# roles is a list of roles to grant to the Bot. Don't worry if you don't know
# what roles you need to specify here, the Access Guides will walk you through
# creating and assigning roles to the already created Bot.
roles: []

Make sure you replace example with a unique, descriptive name for your Bot.

Use tctl to apply this file:

$ tctl create bot.yaml

Step 3/5. Create a tpm join token

With the Bot created, we now need to create a token. The token will be used by tbot to authenticate as the Bot to the Teleport cluster.

Determining the EKPub Hash or EKCert Serial for your TPM

First, you need to determine the characteristics of the TPM on the host that you wish to use Machine ID on. These characteristics will then be used within the allow rules of the join token to grant access to this specific host.

On the machine, run tbot tpm identify:

$ tbot tpm identify
TPM Information
EKPub Hash: 6c5aada1c5abee6d869369a0example2fd2beb41c850d3f0227f029c4fffc4ba
EKCert Detected: true
EKCert Serial: 5e:cd:5f:8e

Take the long hexadecimal string after EKPub Hash and assign it to ek-public-hash. This uniquely identifies this TPM and will be used in the join token.

Obtaining the manufacturer CA

If in the previous step, EKCert Detected was false, then you can disregard this section.

If in the previous step, EKCert Detected was true, then it is recommended to obtain the manufacturer's CA certificate. This will allow the TPM to be validated as legitimately manufactured as part of the join process.

Instructions for obtaining the EKCert CA will vary from TPM to TPM. Consult your TPM's documentation for more information or contact your supplier.

Creating the join token

Create a file named bot-token.yaml:

kind: token
version: v2
metadata:
# name identifies the token. Try to ensure that this is descriptive.
name: my-bot-token
spec:
# For Machine ID and TPM joining, roles will always be "Bot" and
# join_method will always be "tpm".
roles: [Bot]
join_method: tpm

# bot_name specifies the name of the bot that this token will grant access to
# when it is used.
bot_name: my-bot

# tpm specifies the TPM join method specific configuration for this token.
tpm:
# ekcert_allowed_cas is a list of CA certificates that will be used to
# validate TPM EKCerts. These should be PEM wrapped.
#
# When specified, joining TPMs must present an EKCert signed by one of the
# specified CAs. TPMs that do not present an EKCert will be not permitted to
# join.
ekcert_allowed_cas:
- |
-----BEGIN CERTIFICATE-----
... CA Certificate Data ...
-----END CERTIFICATE-----
# allow is a list of Rules, the presented TPM must match one allow rule to
# be permitted to join using this token.
allow:
# description is a human-readable description of the rule. It has no
# bearing on whether a TPM is allowed to join, but can be used to
# associate a rule with a specific host (e.g the asset tag of the server
# in which the TPM resides).
- description: "example-server-100"
# ek_public_hash is the SHA256 hash of the EKPub marshaled in PKIX format
# and encoded in hexadecimal. This value will also be checked when a TPM
# has submitted an EKCert, and the public key in the EKCert will be used
# for this check.
ek_public_hash: "ek-public-hash"

If your TPM includes an EKCert and you have obtained the manufacturer's CA, replace the ekcert_allowed_cas section with the PEM wrapped CA certificate. Otherwise, remove this section.

If you have multiple hosts that you wish to authenticate as the same Bot, you can add additional rules the allow list, one for each host.

Apply this to your Teleport cluster using tctl:

$ tctl create -f bot-token.yaml

Step 4/5. Configure tbot

Create /etc/tbot.yaml:

version: v2
proxy_server: example.teleport.sh:443
onboarding:
join_method: tpm
token: my-bot-token
storage:
type: directory
path: /var/lib/teleport/bot
# outputs will be filled in during the completion of an access guide.
outputs: []

Replace:

  • example.teleport.sh:443 with the address of your Teleport Proxy.

Prepare the storage directory

The tbot service requires a way to store its state, such as internal credentials, across restarts. This is known as the storage destination.

For this example, we will use the directory /var/lib/teleport/bot.

As this directory will store the bots sensitive credentials, it is important to protect it. To do this, you will configure the directory to only be accessible to the Linux user which tbot will run as.

Execute the following, replacing teleport with the Linux user that you will run tbot as:

# Make the bot directory and assign ownership to teleport user
$ sudo mkdir -p /var/lib/teleport/bot
$ sudo chown teleport:teleport /var/lib/teleport/bot

Create a systemd service

By default, tbot will run in daemon mode. However, this must then be configured as a service within the service manager on the Linux host. The service manager will start tbot on boot and ensure it is restarted if it fails. For this guide, systemd will be demonstrated but tbot should be compatible with all common alternatives.

Use tbot install systemd to generate a systemd service file:

$ tbot install systemd \
--write \
--config /etc/tbot.yaml \
--user teleport \
--group teleport \
--anonymous-telemetry

Ensure that you replace:

  • teleport with the name of Linux user you wish to run tbot as.
  • /etc/tbot.yaml with the path to the configuration file you have created.

You can omit --write to print the systemd service file to the console instead of writing it to disk.

--anonymous-telemetry enables the submission of anonymous usage telemetry. This helps us shape the future development of tbot. You can disable this by omitting this.

Next, enable the service so that it will start on boot and then start the service:

$ sudo systemctl daemon-reload
$ sudo systemctl enable tbot
$ sudo systemctl start tbot

Check the service has started successfully:

$ sudo systemctl status tbot

Step 5/5. Configure outputs

You have now prepared the base configuration for tbot. At this point, it identifies itself to the Teleport cluster and renews its own credentials but does not output any credentials for other applications to use.

Follow one of the access guides to configure an output that meets your access needs.

Next steps