Eit skript som startar OpenVPN og aldri koplar til, er vanlegvis ikkje eit nettverksproblem: klienten sit ved ei ledetekst utan ein terminal å teikne henne på. OpenVPN har nøyaktig to støtta måtar å svare på den ledeteksta utan eit menneske, ei påloggingsfil bak auth-user-pass og styresokkelen, og dei er ikkje utskiftbare. Fila kostar éin direktiv og svarar på éi ledetekst; sokkelen svarar på kvar ledetekst og gjev alt som kan opne ein loopback-port ein uautentisert kontrollkanal. Kva for ei som høyrer til utrullinga di, kjem an på kva ledetekst som faktisk blokkerer, og kva løyndom du har råd til å la liggje i ro.

Namngje ledeteksta før du vel mekanisme

Fire ledetekster ser like ut på ein terminal. Kontoparet kjem frå PAM- eller auth-user-pass-verify-oppsettet på tenaren og vert svara av auth-user-pass. Ein passfrase for ein privat nøkkel høyrer til nøkkelfila og vert lesen via --askpass eller skriven inn for hand. Eit PKCS#12-bundle spør om sitt eige passord. Proxy-autentisering brukar auth-fila som --http-proxy tek, ikkje kontoopplysningane.

Når OpenVPN køyrer som born av systemd, PHP eller Node, finst det ingen terminal, så kvar av desse blokkerer stille. Prosessen sit der, loggen stoppar etter chiffer-linja, og eininga går til slutt i timeout; den stilla er grunnen til at folk legg til ei gjentakingsløkke eller eit sleep i staden for å sjå kva ledetekst som ventar. Berre styresokkelen kan svare på alle fire. Påloggingsfila svarar på den første og ingenting anna.

auth-user-pass: éi fil, éi ledetekst

Fila inneheld brukarnamnet på første linje og passordet på andre, og ingenting anna: ingen hermeteikn, ingen nøkkelnamn, ingen kommentar. Set modus 600 og gjer eigaren til kontoen som køyrer openvpn, som for ein teneste ofte er ein dedikert brukar og ikkje di eiga innlogging. Ei fil som root eig under /root er skilnaden mellom ein kommando som verkar i skalet ditt og ei eining som feilar ved oppstart.

To detaljar gjer ei korrekt fil til ei ledetekst. Ein editor som lagrar CRLF, lèt ein vognretur henge att på passordet, så tenaren avviser eit passord som ser rett ut i fila; sjekk med cat -A eller od -c i staden for med auget. Og ein auth-user-pass utan argument inne i profilen tyder «spør brukaren» etter design, noko ein andre direktiv på kommandolinja kanskje ikkje overstyrer, fordi profilen vert parsa der han ligg.

Rekkefølgja på vala er den tredje fella, og ho er versjonsavhengig. Nokre OpenVPN 2.4-bygg ignorerer --auth-user-pass når det står før --config, så dei same to vala i motsett rekkefølgje koplar til. Set direktivet i profilen, eller etter --config på kommandolinja, og grep profilen for kvar førekomst før du endrar noko anna.

auth-nocache høyrer til denne mekanismen, men leverer ingenting. Det avgrensar kor lenge klienten held påloggingsdata i minnet, noko som hjelper etter ein krasj og slett ikkje når fila manglar. Ei attkopling etter ein sesjonstimeout på tenarsida les fila på nytt, så påloggingsdata som verka ved oppstart, kan framleis gå ut midt på dagen.

Styresokkelen: kvar ledetekst, meir overflate

Start klienten med ein lyttar og sei eksplisitt at ledetekster vil bli rapporterte på han, med direktiva som er dokumenterte i OpenVPN 2.6-handboka:

management 127.0.0.1 3030
management-query-passwords

Frå bash held du sambandet på ein ledig fildeskriptor og svarar etter ledetekstnamn i staden for posisjon, fordi ei attkopling kan spørje i ei anna rekkefølgje:

exec 3<>/dev/tcp/127.0.0.1/3030
while read -r -u 3 line; do
  case "$line" in
    *"Need 'Auth' username/password"*)
      echo 'username "Auth" alice' >&3
      echo 'password "Auth" secret' >&3 ;;
    *"Need 'Private Key' password"*)
      echo 'password "Private Key" secret' >&3 ;;
  esac
done

Grensa er transporten. Styringsprotokollen er klartekst over TCP på loopback, så lyttaren må ikkje publiserast på ei LAN- eller tunneladresse for at ein ekstern kontrollør skal nå han; ein ekstern kontrollør tyder ei SSH-vidaresending, ikkje ei breiare binding. Fellesskapsdæmonen godtek òg berre éin styringsklient om gongen, så ein GUI eller monitor kan ikkje dele sokkelen med skriptet ditt. Den andre sambindinga vert avvist, ikkje sett i kø, og feilen ser ut som eit skript som har vorte døyvt.

Den sokkelen er òg ein kontrollkanal. Utan eit styringspassord kan alt som kan kopie til 127.0.0.1:3030 lese status, drepe tunnelen eller svare på ei ledetekst sjølv. Styringspassordet og påloggingsfila er løyndomar i same klasse, og begge fortener same omhug.

Kva for ei som passar til utrullinga

Vel påloggingsfila når den einaste ledeteksta er kontoparet, klienten køyrer som teneste med ein stabil eigar, og du kan halde ei 600-fil utanfor tryggingskopiar du ikkje styrer. Vel styresokkelen når ein nøkkelpassfrase eller eit PKCS#12-passord er i spel, når innpakninga alt overvakar prosessen, eller når du må følgje med på status og ledetekster medan du feilsøkjer ei attkopling.

To vilkår flyttar avgjerda. Er innpakninga /bin/sh, ei systemd-eining som kallar binærfila direkte, eller ein minimal container, er bash-berre sokkel-lim ikkje tilgjengeleg, og fila er det billegare svaret. Om løyndomen roterer ofte, er inga av filene eit godt heim for han: spør ein nøkkelring frå ei lita innpakning og lat eininga kalle innpakninga, noko som held rotasjonen på éin stad og passordet ute av skalhistorikken.

Prosessubstitusjon står mellom dei to og høyrer til ingen av dei. Den eine linja nedanfor verkar fordi bash utvidar henne før openvpn startar, ikkje fordi klienten forstår syntaksen:

openvpn --config client.ovpn --auth-user-pass <(printf "%s
%s
" "$USER" "$PASS")

Ho brekk under /bin/sh, i ei eining som omgår skalet, og i bilete utan bash eller /dev/fd. Hald henne for interaktiv testing, aldri som kontrakten ein teneste er avhengig av.

Vern løyndomen, og stadfest deretter frå loggen

Båe mekanismane lèt etter seg ein løyndom som OpenVPN-prosessen kan lese. Legg aldri passordet på kommandolinja eller i einingafila, der ps og systemctl viser det til kvar lokal brukar; gje stien til fila, ikkje verdien i henne. Der sertifikat kan erstatte kontoparet, fjernar det ledetekstkategorien i staden for å skjule han.

Ein korrekt køyring viser ledetekstrekkja fullførast og økta nå «Initialization Sequence Completed». Stoppar klienten ved same ledetekst, feila matchinga: skriv ut dei nøyaktige linjene sokkelen sende, sjekk hermeteikn og ledetekstnamnet, og rett mønsteret i staden for å leggje til eit sleep. Ein tunnel som rapporterer suksess og ikkje ber noko, er eit ruting- eller push-problem, ikkje eit påloggingsproblem.

Test deretter attkoplinga, ikkje berre første oppstart. Slipp økta på tenarsida eller vent ut timeouten; klienten spør igjen, og det er der ei fil som såg korrekt ut ved oppstart, viser om ho framleis kan lesast av kontoen som koplar til på nytt.

Relaterte artiklar