Din VPN besvarer forbindelser klokken 3 om natten, mens maskinen, der underskriver dens certifikater, står slukket i en skuffe. En klient, der validerer servercertifikatet, kontakter aldrig din CA, så CA'en behøver ikke at være tilgængelig for nogen forbindelse. Den del, der kræver planlægning, er den dag, hvor et certifikat skal udstedes, fornyes eller tilbagekaldes mens rodnøglen forbliver låst inde.

Hvad en forbindelse faktisk validerer

Når OpenVPN-klienten tilslutter sig, går den gennem signaturkæden fra serverens løvcertifikat op til et CA-certifikat, den allerede stoler på, kontrollerer gyldighedsvinduet og konsulterer, hvis profilen siger det, en tilbagekaldelsesliste. Den slår aldrig din rod-CA op. Serveren gør det spejlvendte for klientcertifikater. På tilslutningstidspunktet er kun løvcertifikatet, mellemcertifikatet og den tillidsbundt, du distribuerede tidligere, til stede.

Det, der faktisk fejler, er en af tre ting: signeringsnøglen er utilgængelig ved udstedelse, en tilbagekaldelsesliste er blevet forældet, eller klientens tillidsbundt er ældre end den kæde, serveren præsenterer. Det første er et procesproblem; de to andre er distributionsproblemer. Ingen af dem kræver, at rodnøglen er online, og en administreret VPN-tjeneste, der kræver et privat certifikat til tunnelgodkendelse, flytter blot signeringsmyndigheden til udbyderen. Azure point-to-site virker den anden vej: du uploader et rodcertifikat, og certifikater signeret under det betragtes som betroede, så spørg, hvem der signerer, hvem der validerer, og hvordan et certifikat trækkes tilbage tidligt.

Byg roden på en vært, der aldrig får en adresse

En offline rod bruges sjældent: til at signere mellemcertifikatet og senere til at forny eller tilbagekalde det. Alt andet sker et niveau længere nede. Udfør rodarbejdet på en maskine, der holdes væk fra netværket, om muligt fra et live-system, og registrer, hvem der var i lokalet. Kommandoerne antager OpenSSL 1.1.1 eller nyere, fordi -addext ikke findes i ældre builds.

openssl genpkey -algorithm EC -pkeyopt ec_paramgen_curve:P-256 -out root.key
openssl req -x509 -new -key root.key -sha256 -days 7300 \
  -subj "/CN=Example VPN Root CA" -out root.crt \
  -addext "basicConstraints=critical,CA:TRUE" \
  -addext "keyUsage=critical,keyCertSign,cRLSign"

Opret mellemcertifikatet på signeringsværten, og bring kun dets anmodning til den offline maskine. Roden signerer anmodningen med en sti-længde på nul, så mellem-CA'en må signere slutpunktscertifikater, men må ikke oprette en ny CA under sig. Den ene udvidelse forhindrer en kompromitteret signeringsvært i at skabe en rodligtærdig myndighed. Brug kun ECDSA, hvis hver klient kører OpenVPN 2.4 eller nyere; generér ellers RSA-nøgler, og hold flowet identisk.

openssl genpkey -algorithm EC -pkeyopt ec_paramgen_curve:P-256 -out intermediate.key
openssl req -new -key intermediate.key -subj "/CN=Example VPN Intermediate CA" -out intermediate.csr
openssl x509 -req -in intermediate.csr -CA root.crt -CAkey root.key \
  -CAcreateserial -days 3650 -sha256 -extfile intermediate.ext -out intermediate.crt

intermediate.ext indeholder basicConstraints=critical,CA:TRUE,pathlen:0, keyUsage=critical,keyCertSign,cRLSign og authorityKeyIdentifier=keyid:always. Læg rodnøglen tilbage i dens boks, før signeringsværten tilsluttes igen. Hvis roden skal kunne tilbagekalde mellemcertifikatet, skal du signere det med openssl ca -config root.cnf -extensions intermediate_ca mod en index.txt på rodniveau i stedet for openssl x509 -req, så serienummeret registreres; send derefter den resulterende rodliste ind i klientprofilen, hvor en filbaseret crl-verify læser den ved opstart. Send klienter et bundt med begge CA-certifikater; et løvcertifikat alene validerer ikke mod roden.

Udsted løvcertifikater fra mellemleddet, med en database

Signering med openssl x509 -req virker, indtil du skal tilbagekalde, fordi intet registrerer serienummeret. Brug openssl ca fra det første certifikat, så serienummer, udløb og tilbagekaldelsesstatus lever i én database. Opret databasefilerne én gang, og peg derefter konfigurationen på dem:

mkdir -p /etc/vpn-ca/intermediate/newcerts
touch /etc/vpn-ca/intermediate/index.txt
echo 1000 > /etc/vpn-ca/intermediate/serial
echo 1000 > /etc/vpn-ca/intermediate/crlnumber
[ ca ]
default_ca = CA_default
[ CA_default ]
dir = /etc/vpn-ca/intermediate
database = $dir/index.txt
new_certs_dir = $dir/newcerts
serial = $dir/serial
crlnumber = $dir/crlnumber
certificate = $dir/intermediate.crt
private_key = $dir/intermediate.key
default_md = sha256
default_days = 365
default_crl_days = 30
unique_subject = no
policy = policy_any
[ policy_any ]
commonName = supplied
[ server_cert ]
basicConstraints = CA:FALSE
keyUsage = critical, digitalSignature
extendedKeyUsage = serverAuth
subjectAltName = @server_names
[ client_cert ]
basicConstraints = CA:FALSE
keyUsage = critical, digitalSignature
extendedKeyUsage = clientAuth
[ server_names ]
DNS.1 = vpn.example.com

Linjen for nøglebrug antager en ECDSA-nøgle; tilføj keyEncipherment til RSA. Giv hver klient sit eget fælles navn, fordi OpenVPN identificerer en forbindelse på det felt, og to bærbare computere, der deler CN=vpn-client, kan ikke skelnes i logfiler, i client-config-dir-regler eller i nogen push pr. bruger, og du mister den tilskrivning, der gør en tilbagekaldelsesbeslutning forsvarlig. Udsted og valider et løvcertifikat sådan:

openssl req -new -key alice.key -subj "/CN=alice-laptop" -out alice.csr
openssl ca -config intermediate.cnf -extensions client_cert -in alice.csr -out alice.crt -batch
openssl verify -CAfile ca-bundle.crt -untrusted intermediate.crt alice.crt

Hold signeringsnøglen bag en politikgrænse i stedet for at kopiere den til VPN-værten: en lille tjeneste, der godkender anmodningen, kontrollerer det fælles navn mod en tilladelsesliste og kun returnerer certifikatet. Log hvert serienummer; loggen er det eneste bånd mellem et certifikat og den person, der bad om det.

Udgiv tilbagekaldelse uden at vække roden

Klientcertifikater tilbagekaldes af mellemleddet, aldrig af roden. Rodlisten betyder kun noget, når et mellemled er brændt. Peg serveren på mellemlisten med crl-verify. En filbaseret CRL indlæses ved tjenestestart, så genindlæs efter hver regenerering; mappeformen læser tilstand ved tilslutning og koster én fil pr. serienummer.

Tilbagekald og regenerér med to kommandoer fra samme database:

openssl ca -config intermediate.cnf -revoke /etc/vpn-ca/intermediate/newcerts/1001.pem
openssl ca -config intermediate.cnf -gencrl -out /etc/openvpn/crl.pem

Hold så øje med uret. En CRL bærer et felt for næste opdatering, og når den dato er passeret, afviser en validerende part listen i stedet for at ignorere den. Månedlig regenerering med default_crl_days = 30 giver luft; årlig regenerering gør ikke. Kortere løvcertifikatlevetider er den mere pålidelige kontrol, fordi tilbagekaldelse kun gælder, hvor listen konsulteres.

Test kæden, og skriv derefter ceremonien ned

Gengiv fire fejl, før du stoler på designet. Validér kæden med openssl verify -CAfile ca-bundle.crt -untrusted intermediate.crt server.crt. Tilslut med et udløbet klientcertifikat, og bekræft, at serveren afviser det. Tilbagekald en testklient, genindlæs, og bekræft, at listen træder i kraft. Flyt en værts ur en dag frem, fordi et forkert ur kan udstede og afvise certifikater, der ser gyldige ud andre steder.

En offline rod er kun en kontrol, hvis papirarbejdet findes: to navngivne personer til ceremonien, en registrering af hvert signeret serienummer, en krypteret backup opbevaret adskilt fra maskinen og en gendannelsestest på en isoleret vært. Signer et ekstra mellemcertifikat under samme ceremoni, så en død signeringsvært ikke tvinger dig til at låse roden op ved midnat.

Før du kalder det færdigt, bekræft fem ting: rodnøglen er ikke på en netværkstilsluttet vært, mellemnøglen lever kun på signeringsværten, klientbundtet bærer begge CA-certifikater, CRL'en har en fremtidig næste opdatering, og nogen ejer en kalenderpost for hvert udløb i kæden. Hvis én mangler, er opsætningen, der ser offline ud, blot udokumenteret.

Relaterede artikler