This episode integrates Kerberos into SSH via GSSAPI: sshd and client configuration, creating host principals and keytabs, the single sign-on flow, the difference between ForwardAgent and credential delegation, and troubleshooting when GSSAPI authentication fails.

In episode 12 we secured the initial identity proof with preauth and FAST — now it's time to reap the benefits. Imagine a sysadmin managing 50 servers: typing passwords 50 times every morning, or distributing SSH public keys to 50 machines, then revoking them one by one when an employee leaves. Kerberos turns all of that into a single login. In this episode we connect our ticket protocol to SSH through GSSAPI — the road to single sign-on in the network world.
SSH has been secure for a long time through passwords or public keys. So why bother with Kerberos? Because both have administrative weaknesses: passwords mean typing them over and over, and passwords leak through the process; public keys mean distribution (placing the key on every machine) and revocation (revoking the access of a departing employee) scattered everywhere. Kerberos centralizes all of it: disable the principal on the KDC, and all of that user's SSH access stops at once, everywhere.
GSSAPI (Generic Security Services Application Program Interface) is a standard interface that lets applications negotiate security without knowing the mechanism behind it. In the Linux world, the most common GSSAPI mechanism is Kerberos 5. When you say "SSH using GSSAPI", it means: SSH uses the GSSAPI interface, and the GSSAPI implementation (usually libgssapi-krb5) runs Kerberos behind the scenes.
Because GSSAPI is a standard, clients and servers can exchange security tokens with uniform rules. These tokens carry the Kerberos service ticket during login.
Let's follow the journey of alice who wants to ssh alice@server.example.com:
kinit and obtains a TGT.ssh is run, the client requests GSSAPI authentication. SSH takes alice's TGT, then requests a service ticket for the principal host/server.example.com from the KDC.sshd receives the token, decrypts it with its own keytab, and reads alice's identity from the ticket.No password traverses the network, and no public key of alice needs to be stored on the server. The server needs only one thing: a keytab containing the host/server.example.com key.
On the server side, make sure the SSH daemon is willing to accept GSSAPI authentication. Edit /etc/ssh/sshd_config:
# Authentication via GSSAPI (Kerberos)
GSSAPIAuthentication yes
# Remove Kerberos credentials after the login session ends
GSSAPICleanupCredentials yes
# Allow GSSAPI-based host key exchange
GSSAPIKeyExchange yesAfter changing this, sshd needs to read a key matching its Kerberos identity. That key is stored in a keytab — by default /etc/krb5.keytab — and must contain the principal host/server.example.com. Create and extract the key via kadmin:
kadmin.local -q "addprinc -randkey host/server.example.com"
kadmin.local -q "ktadd -k /etc/krb5.keytab host/server.example.com"Verify that the keytab contains the correct entry:
klist -k /etc/krb5.keytabImportant
Keytab security is absolute: the keys inside are the server's identity in the Kerberos world. Make sure the keytab can only be read by root (chmod 600 /etc/krb5.keytab). Anyone who steals a keytab can impersonate the server — the case we discuss in troubleshooting below is the most common symptom of a missing or wrong keytab.
One thing often forgotten: the principal name must exactly match the hostname the client uses. If alice types ssh server.example.com, the requested service ticket is host/server.example.com. If alice types just ssh server (without the FQDN), the request becomes host/server — and fails because that principal doesn't exist on the KDC. This is a classic source of errors, and the way to avoid it is ensuring clients always use the FQDN.
On the client side, kinit must succeed first, then SSH needs to be allowed to try GSSAPI. Edit /etc/ssh/ssh_config (or in the per-user file ~/.ssh/config):
Host *.example.com
GSSAPIAuthentication yes
GSSAPIDelegateCredentials yes
GSSAPIKeyExchange yesThe line GSSAPIDelegateCredentials yes is important if you want to continue the Kerberos journey from the destination server (multi-hop). We dissect the details in the next section.
From the command line, the fastest way is the -K flag, which enables GSSAPI credential delegation:
ssh -K alice@server.example.comThen verify the tickets formed on the destination server:
klistIf a TGT for alice@EXAMPLE.COM appears in the server's cache, credential delegation is working.
This is where many people get confused. There are two ways to "continue access" from one server to another:
ForwardAgent) — forwards the SSH agent socket. That means processes on the destination server can borrow the SSH private key stored on the client machine to authenticate to the next hop. What's forwarded is the public/private key.GSSAPIDelegateCredentials) — forwards the Kerberos ticket (TGT). Processes on the destination server can request new Kerberos service tickets on your behalf. What's forwarded is a ticket, not a key.The choice depends on the ecosystem: if your entire network is already Kerberized, GSSAPI delegation is more natural and easier to revoke (tickets have a lifetime, keys don't). If there are still machines that only know SSH keys, agent forwarding is the helper. Also note the delegation risk: a delegated ticket gives full power over your identity on the destination server, so only enable it on jump hosts you trust — not on just any server.
When ssh refuses and you see a password prompt (meaning GSSAPI was skipped), debugging starts with SSH's most honest message: verbose logging.
ssh -vvv alice@server.example.comLook for lines mentioning gssapi or Authentications that can continue. Some of the most common failures:
1. Principal not in the keytab. The message Server not found in Kerberos database (or no principal in keytab) means the server keytab doesn't contain host/server.example.com — even though the client requested it. Check with klist -k /etc/krb5.keytab and match it against the FQDN the client uses.
2. Realm not recognized. If the client thinks its realm differs from the server's, the ticket exchange fails. Make sure default_realm in /etc/krb5.conf is consistent on both sides, and that the server hostname can be mapped to a realm via [domain_realm].
3. Client ticket expired or missing. Run klist — if empty, kinit first. Weird errors like Clock skew too great also appear if machine clocks drift (remember preauth in episode 12).
4. Keytab with wrong permissions. sshd running as root needs to read the keytab. A keytab with permission 0666 is a security hazard; a keytab with overly strict permissions but the wrong owner will also be denied read access.
5. Delegation not allowed. If ssh -K logs in successfully but klist on the server is empty, chances are GSSAPIDelegateCredentials is off on the client side, or the server doesn't return a delegated ticket because ok-as-delegate on the client principal isn't allowed.
Tip
The right reflex when GSSAPI fails: check klist on the client first (do you have a ticket?), then klist -k on the server (does the principal exist?), then ssh -vvv to see the exact message. The majority of "Kerberos SSH doesn't work" cases are resolved with just those first two commands.
In this episode we transformed SSH from a scattered authentication system into part of the SSO ecosystem: GSSAPI as the standard bridge, the host principal host/server.example.com in the keytab as the server's identity, GSSAPIAuthentication in sshd_config, GSSAPIDelegateCredentials and ssh -K for ticket forwarding, the fundamental difference between agent forwarding and credential delegation, and a targeted troubleshooting flow.
The core of this episode: Kerberized SSH turns server identity from stored keys into centralized tickets — one account dies on the KDC, all of that user's SSH access goes dark at once. It's a small configuration investment that pays off big in daily administration.
In episode 14 we follow the same principle into shared data: NFS with Kerberos (sec=krb5) — protecting file shares from IP spoofing, no integrity, and no encryption, into a service that verifies who the real user is. See you there!