Tjenesten starter, loggen klager på at den ikke kan åpne tun-enheten, og ruter dukker aldri opp. Kjør capsh --print i skallet ditt, og cap_net_admin er rett der, noe som gjør feilen umulig å forklare. Det som skiller skallet ditt fra uniten er privilegieovergangen, ikke kjernens vilje til å gi kapabiliteten. Gå gjennom de fire kontrollene nedenfor i rekkefølge og stopp ved den første som forklarer forskjellen.

Skill en manglende kapabilitet fra en skjult enhet

To feil ser like ut i logglinjen. En prosess uten CAP_NET_ADMIN kan ikke opprette eller konfigurere tunellgrensesnittet, og en prosess der sandkassen skjuler /dev/net/tun kan ikke åpne det i det hele tatt. Å legge til kapabiliteter retter ikke det andre tilfellet.

Kontroller om enheten finnes inne i tjenestens navnerom før du endrer noe. PrivateDevices=yes er en vanlig herdingslinje som fjerner tun-noden helt, og en restriktiv ProtectSystem kan gjøre konfigurasjonsstien skrivebeskyttet på en måte som leses som en tilgangsfeil. Begge gir logglinjer som nevner tunellen, og derfor får kapabilitetene skylden. Bekreft først at noden finnes og kan åpnes, og gå så videre.

Vit hvilket kapabilitetssett du ser på

Linux holder permiterte, effektive, arvbare, begrensende og ambiente sett, og det ambiente settet er det som overlever en exec fra en bruker som ikke er root. Filkapabiliteter på binæren kan overlevere permiterte og effektive rettigheter ved exec, men bare så lenge ingenting i kjeden blokkerer den overføringen.

Det er her sudo villeder folk. En kommando som kjøres gjennom sudo -u, starter en ny privilegieovergang og det ambiente settet er borte, så den samme kontrollen som lykkes som root feiler der. Tjenestebehandleren er nok en overgang, og den gir ingenting ambient med mindre uniten sier det.

Gi kapabiliteten i uniten, ikke i en wrapper

En minimal tjenesteseksjon for en tunell som må opprette en enhet og installere ruter ser slik ut.

[Unit]
Description=OpenVPN client, office profile
After=network-online.target

[Service]
Type=notify
User=openvpn
Group=openvpn
NoNewPrivileges=yes
AmbientCapabilities=CAP_NET_ADMIN
CapabilityBoundingSet=CAP_NET_ADMIN
ExecStart=/usr/sbin/openvpn --config /etc/openvpn/office.conf

AmbientCapabilities setter rettigheten i det ambiente settet før prosessen starter, og CapabilityBoundingSet hindrer prosessen i å holde noe utenfor den listen. NoNewPrivileges=yes blokkerer privilegieoppnåelse gjennom setuid eller filkapabiliteter, mens kapabiliteten uniten gir uttrykkelig, fortsatt gjelder. Legg bare til CAP_NET_BIND_SERVICE når tjenesten må binde en lav port, og legg aldri til CAP_SYS_ADMIN bare fordi en forumtråd gjorde det.

Hvis uniten pakker binæren inn i sudo, fjern wrapperen. systemd anvender allerede User=, og det ekstra laget er den mest sannsynlige grunnen til at det ambiente settet er tomt.

Verifiser mot den levende prosessen, ikke unitfilen

Les hva behandleren faktisk anvendte, og les deretter prosessen den startet.

unit=openvpn-client@office
systemctl show -p User -p AmbientCapabilities "$unit"
systemctl show -p MainPID --value "$unit" | xargs -r getpcaps
grep -E '^Cap(Eff|Amb)' /proc/$(systemctl show -p MainPID --value "$unit")/status

Hvis uniten lister kapabiliteten og CapEff fortsatt mangler den, overstyrer en drop-in innstillingen eller et ExecStartPre-trinn endrer miljøet. Søk i drop-in-katalogene etter unitnavnet før du antar at hovedfilen er autoritativ, fordi en senere fil vinner i stillhet. Hvis både uniten og prosessen viser kapabiliteten og tunellen fortsatt feiler, gå tilbake til enhets- og stikontrollene i stedet for å utvide det begrensende settet. Å utvide det skjuler den egentlige årsaken og etterlater tjenesten mer privilegert enn den var.

Foretrekk å gi slipp på privilegier etter oppstart

OpenVPN kan starte med privilegier og deretter gå over til en uprivilegert konto via sine egne user- og group-valg, mens persist-key og persist-tun holder tunellen brukbar etterpå. Den ordningen snevrer inn vinduet der prosessen har rettigheter, og den passer ofte bedre enn å starte hele daemonen uprivilegert med permanente kapabiliteter.

Uansett hvilken modell du velger, start uniten på nytt og gjenta kontrollene etter en omstart, fordi en tjeneste som virker fra et interaktivt root-skal og feiler ved oppstart, vanligvis er en forskjell i kapabilitet, enhet eller filrettigheter. Noter unitinnstillingene ved siden av prosessens kapabilitetsutdata, slik at neste anmelder kan se om en pakkeoppdatering eller en drop-in har flyttet grensen.

Relaterte artikler