IPsec

Running a Cisco Router as a CA Server: PKI You Can Lab

IOS CA server: real show crypto pki server output showing an enabled CA with its fingerprint
In: IPsec, VPN, PKI, CCIE, Labs

PKI is one of those topics that everyone nods along to and almost nobody has actually built. You read about certificate authorities, trustpoints, enrollment, and revocation, and it all stays abstract because the tooling feels heavy: a Windows domain, AD CS, a public CA that wants money and a DNS record. So the chapter gets skimmed, and then one day a certificate-authenticated IPsec tunnel refuses to come up and you are debugging something you never actually saw work.

Here is the shortcut. You do not need any of that. A Cisco IOS XE router will happily act as a full certificate authority, issue real X.509 certificates, and hand them to other routers over HTTP. It takes about six lines of config. In our CCIE Security lab we built exactly that on a cat8000v called CA1, issued real certificates from it, and then used those certificates to authenticate an IKEv2 tunnel with no pre-shared key anywhere in the configuration. If you are working through the IPsec VPN pillar, this is the missing piece that makes certificate authentication stop being theory.

What a Certificate Authority Actually Does

Strip away the ceremony and a CA does two things.

First, it issues itself a certificate. This is the root, and it is self-signed: the CA vouches for itself, because there is nobody above it to do the vouching. In our lab this was serial number 01. That self-signed CA certificate is what every client will eventually install and trust. Everything downstream hangs off it.

Second, it signs certificate signing requests (CSRs) from clients. A router generates an RSA keypair, keeps the private key, wraps the public key plus a subject name into a CSR, and sends it to the CA. The CA checks it (or, in a lab, does not check it at all), signs it with the CA private key, and hands back an identity certificate. In our lab GM1 got serial 02 and GM2 got serial 03.

The Config: Six Lines and a Reload of Your Assumptions

This is the CA server we built on CA1 (a cat8000v at 10.100.0.31 on the lab WAN core):

CA1(config)#crypto pki server PLZ-CA
 database level complete
 issuer-name CN=PLZ-CA,O=PingLabz,C=US
 grant auto
 lifetime certificate 730
 lifetime ca-certificate 1825
 no shutdown

Line by line:

crypto pki server PLZ-CA
Creates the CA and names it. The name matters: it becomes the trustpoint the CA uses for its own key, and it is what you reference in every show command.
database level complete
Write a full copy of every issued certificate to storage as <serial>.cer. The alternatives (minimal, names) store less. You want complete if you ever intend to revoke anything, because you need the certificate to revoke it.
issuer-name CN=PLZ-CA,O=PingLabz,C=US
The distinguished name that appears as the Issuer field on every certificate this CA signs. This is the CA's identity on the wire.
grant auto
Sign every CSR that arrives, automatically, no questions asked. Wonderful for a lab. Read the warning below before you even think about it anywhere else.
lifetime certificate 730
Issued identity certificates are valid for 730 days (two years). Shorter lifetimes are better security hygiene, and worse operational ergonomics if you have no automatic re-enrollment.
lifetime ca-certificate 1825
The CA's own root certificate lives for 1825 days (five years). It must outlive every certificate it signs, or you get a very bad day at renewal time.

About grant auto, honestly

grant auto means the CA signs anything that asks. Any device that can reach TCP/80 on the CA and speak SCEP gets a valid certificate with whatever subject name it claimed. In a closed lab that is exactly what you want, because the alternative is manually approving every enrollment while you are trying to learn something else.

In production it is the opposite of what you want. The correct setting is grant none, which parks every request in a queue. You then inspect the request, confirm out of band that the device asking is the device you think it is, and approve it explicitly with crypto pki server PLZ-CA grant <req-id>. That manual step is not bureaucracy, it is the entire point: a CA that signs anything is a CA that will happily issue a certificate to an attacker who plugged a laptop into your network and claimed to be a router. The certificate would be cryptographically perfect and completely worthless.

Before: Configured but Disabled

Type the config but do not enable the server, and this is what you get. This is real output from CA1:

CA1#show crypto pki server
Certificate Server PLZ-CA:
    Status: disabled
    State: initial
    Server's configuration is unlocked  (enter "no shut" to lock it)
    Issuer name: CN=PLZ-CA,O=PingLabz,C=US
    CA cert fingerprint: -Not found-
    Granting mode is: auto

Four things are being told to you here.

Status: disabled / State: initial. The CA exists as configuration but has done nothing. It has no keypair and no certificate.

Server's configuration is unlocked (enter "no shut" to lock it). This is the interesting one. While the server is shut down, you can freely change the issuer name, the lifetimes, the whole shape of the CA. The moment you enable it, the identity-defining parameters lock, because the CA is about to generate a self-signed certificate that bakes them in. You cannot rename an issuer after it has signed certificates without invalidating everything downstream. IOS enforces that for you.

CA cert fingerprint: -Not found-. There is no CA certificate yet, so there is nothing to fingerprint. This field is going to matter enormously in a minute.

Granting mode is: auto. Exactly what we asked for, and exactly what we would not ask for in production.

After: A Live CA With a Real Fingerprint

Now enable it with no shutdown, answer the prompts, and look again:

CA1#show crypto pki server
Certificate Server PLZ-CA:
    Status: enabled
    State: enabled
    Server's configuration is locked  (enter "shut" to unlock it)
    Issuer name: CN=PLZ-CA,O=PingLabz,C=US
    CA cert fingerprint: 50AE2189 0FC62684 1418DEF0 B0EB714A
    Granting mode is: auto
    Last certificate issued serial number (hex): 3
    CA certificate expiration timer: 09:04:14 UTC Jul 12 2031
    CRL NextUpdate timer: 15:04:24 UTC Jul 13 2026
    Current primary storage dir: nvram:
    Database Level: Complete - all issued certs written as <serialnum>.cer

Walk the new fields:

Status: enabled / State: enabled. The CA has generated its RSA keypair, signed its own root certificate, and is now listening for enrollment requests over SCEP on HTTP.

Server's configuration is locked. As promised. The issuer name is now cast in the root certificate.

CA cert fingerprint: 50AE2189 0FC62684 1418DEF0 B0EB714A. Memorize this idea, not the value. This is the fingerprint of the CA's self-signed root certificate. When a client later runs crypto pki authenticate, IOS will display a fingerprint and ask whether you accept the certificate. That fingerprint must match this one. Comparing them, out of band, is the only thing standing between you and trusting an impostor CA. We go into this in depth in the walkthrough on certificate authentication for IPsec, but note that the value you compare against originates right here, on the CA itself.

Last certificate issued serial number (hex): 3. Three certificates exist in this CA's world. Serial 01 is the CA's own self-signed root. Serial 02 is GM1's identity certificate. Serial 03 is GM2's. Serials are sequential and never reused, because a serial number plus an issuer name is the unique key for a certificate, and that is precisely what a revocation list refers to.

CA certificate expiration timer: 09:04:14 UTC Jul 12 2031. Five years out, which is our lifetime ca-certificate 1825. When this expires, every certificate chaining to it dies with it. Put it in a calendar.

CRL NextUpdate timer. The CA is publishing a certificate revocation list and telling clients when to come back for a fresh copy. In our lab nothing checks it (more on that shortly), but the CA is dutifully maintaining it anyway.

Current primary storage dir: nvram:. The certificate database, and the CA's private key, live in the router's NVRAM. Sit with that for a second. We will come back to it.

Gotcha 1: no shutdown Is Interactive, and That Kills Automation

You cannot push a CA server config from a script. Not with a naive config push, anyway.

no shutdown under crypto pki server is an interactive command. IOS stops and prompts you for a passphrase, which is used to protect the CA's private key in NVRAM. It then asks you to confirm it. A configuration-automation tool that streams lines at a device and does not handle prompts will hang, time out, or silently leave the CA disabled while reporting success. We hit exactly this: the config went in fine, the server stayed down, and we ended up driving no shutdown from a real interactive SSH session to get past the passphrase prompt.

The lesson generalizes past PKI. Crypto commands in IOS have a habit of being interactive precisely because they involve secrets that should not sit in a config file, and secrets that should not sit in a config file are exactly the things your automation pipeline is worst at handling. If you are building CA bring-up into an automated workflow, you need something that speaks expect-style prompt handling, not a template renderer.

Gotcha 2: PKI Needs a Clock. Set It First.

This is the one that produces the most baffling failures, and here is the router telling you about it in plain English:

%PKI-2-NON_AUTHORITATIVE_CLOCK: PKI functions can not be initialized until an
authoritative time source, like NTP, can be obtained.

Certificates are time-bound objects. Every certificate carries a start date and an end date, and every validation checks the current time against them. If a device's clock is wrong, one of two things happens: it decides a perfectly valid certificate is not yet valid, or it decides an expired certificate is fine. Both are wrong, and neither of them produces an error message that says "your clock is wrong". You get an authentication failure, or a tunnel that will not establish, and you go hunting through crypto debugs for an hour.

Do this before you touch any PKI command, on the CA and on every client:

clock set 09:00:00 Jul 13 2026
ntp server 10.100.0.11

Set the clock manually to get past the bootstrap problem, then point at NTP so it stays right. In a lab, one device with a stable clock acting as the NTP master for everyone else is enough. In production, this is non-negotiable infrastructure: your PKI is only as trustworthy as your time.

What a Lab CA Is Not

Everything above is genuinely real PKI. The certificates are real X.509 certificates, the signatures are real RSA signatures, and the authentication that follows is real cryptographic authentication. But be honest with yourself about the gap between this and a CA you would put behind a bank.

No HSM
The CA private key sits in the router's NVRAM, protected by a passphrase you typed. A real root CA keeps its key in a hardware security module that will not export it under any circumstances, and lives offline in a safe. Ours lives in a VM.
No offline root
Serious PKI uses an offline root that signs one thing (an intermediate CA) and then goes back in the safe. The online intermediate does the day-to-day issuing, so a compromise does not burn the root. We have one CA doing both jobs.
No real revocation
The CA maintains a CRL, but nothing distributes it properly and, in our lab, no client checks it (revocation-check none). Revocation that nobody checks is revocation that does not exist.
grant auto
Anything that can reach the CA gets a certificate. There is no identity proofing, no registration authority, no human in the loop. That is a fine trade in a closed lab and an unacceptable one anywhere else.
Single point of failure
One router. Lose it and you lose the CA key, the certificate database, and your ability to issue or revoke anything. No backup, no key escrow, no recovery plan beyond rebuilding from scratch.
Where it IS good
Learning PKI properly. CCIE and CCNP Security lab work. Small internal deployments where the router population is closed, known, and you control every device on the network.

What To Do With It Next

A CA on its own is inert. It becomes interesting the moment a client enrolls with it and then uses the resulting certificate to prove its identity to a peer. That is the payoff, and it is the subject of the follow-up: certificate authentication for IPsec, where GM1 and GM2 enroll against this exact CA and then bring up an IKEv2 tunnel whose configuration contains no pre-shared key at all. The IKEv2 SA on that tunnel says Auth sign: RSA instead of Auth sign: PSK, and that single word is what all of this was for.

If IKEv2 itself is still fuzzy, start with how IKEv2 works and the wider IPsec VPN guide, which covers the full progression from pre-shared keys through certificates to GETVPN.

Key Takeaways

  • An IOS XE router is a fully functional certificate authority. Six lines of config under crypto pki server and you have a working CA issuing real X.509 certificates. No AD CS, no public CA, no money.
  • The CA issues itself a self-signed root certificate (serial 01 in our lab), then signs client CSRs sequentially (02 for GM1, 03 for GM2). Serial number plus issuer name is what uniquely identifies a certificate, and it is what a CRL revokes.
  • Server's configuration is unlocked becomes locked when you enable the server, because the issuer name is now baked into the self-signed root. Get the issuer name right before you enable.
  • The CA cert fingerprint from show crypto pki server is the value clients must verify out of band when they authenticate the trustpoint. It is the anchor of the entire trust chain.
  • no shutdown on a crypto PKI server is interactive: it prompts for a passphrase protecting the CA private key. A config-push tool that cannot handle prompts will not bring your CA up. Drive it from a real session.
  • PKI needs an authoritative clock. %PKI-2-NON_AUTHORITATIVE_CLOCK means PKI will not even initialize. Set the clock or run NTP on the CA and every client before you touch a single PKI command.
  • grant auto is a lab convenience that signs anything that asks. Production wants grant none and manual approval of every request.
  • A router CA has no HSM, no offline root, no meaningful revocation distribution, and its private key lives in NVRAM. It is excellent for learning and internal labs. It is not a production trust anchor.
Written by
More from Ping Labz
Great! You’ve successfully signed up.
Welcome back! You've successfully signed in.
You've successfully subscribed to Ping Labz.
Your link has expired.
Success! Check your email for magic link to sign-in.
Success! Your billing info has been updated.
Your billing was not updated.