LudovicRousseau / PCSC

pcsc-lite: PC/SC implementation
https://pcsclite.apdu.fr/
Other
270 stars 109 forks source link

systemd service hardening for pcscd #207

Open davidfields opened 3 months ago

davidfields commented 3 months ago

I was curious if systemd service hardening had been discussed within this project, so I searched and came across an email [1] from June 2019 (also the to-do list [2]). I understand this may be a low-priority, but I thought I would contribute what I can.

Below is a drop-in configuration for pcscd.service that I have been using for a couple of months. For ease of reference, I have listed the directives in the order that they appear in the systemd.exec man page [3].

My distro is Arch. My pcsc-lite is from the Arch official repos, and I update my system frequently so the version would be whatever is there at any given time. The same would be true of any other relevant software. The only smartcards I currently have access to and have used with this are various Yubikey 5 series. My workflow as it relates to testing functionality is fairly limited. I mainly use Yubikey PIV with OpenSSH via PKCS#11 (opensc-pkcs11).

(I originally wrote this using trial and error, and while doing the same for a handful of other services.)

[Service]
# Paths
ProtectProc=invisible

# Capabilities
CapabilityBoundingSet=

# Security
NoNewPrivileges=yes

# Process Properties
UMask=0077

# Sandboxing
ProtectSystem=strict
ProtectHome=yes
PrivateTmp=yes
#PrivateDevices=yes
PrivateNetwork=yes
#PrivateIPC=yes
PrivateUsers=yes
ProtectHostname=yes
ProtectClock=yes
ProtectKernelTunables=yes
ProtectKernelModules=yes
ProtectKernelLogs=yes
ProtectControlGroups=yes
RestrictAddressFamilies=~AF_INET AF_INET6
RestrictNamespaces=yes
LockPersonality=yes
MemoryDenyWriteExecute=yes
RestrictRealtime=yes
RestrictSUIDSGID=yes
#RemoveIPC=yes
#PrivateMounts=yes

# System Call Filtering
SystemCallFilter=@system-service
SystemCallFilter=~@resources @privileged
SystemCallArchitectures=native

The commented out directives are ones that, when I wrote this a few months ago, I had either tested and they definitely caused things to break, or I had not yet tested.

Looking at the commented out directives now:

There are some other directives that I am deliberately ignoring for now, such as User= or DynamicUser=, as well as directives that lock down the paths for various things. I am ignoring them not because they are unimportant (they are important), but because I think, if there is interest, we could make progress by first getting some of the easier ones out of the way...

Additionally, there is likely room to further lock down RestrictAddressFamilies= and SystemCallFilter=.

I will also note that some of these hardening directives may not currently do anything while the service runs as root. Off the top of my head, I believe this is the case for ProtectProc=invisible and RemoveIPC=yes.

systemd-analyze security pcscd.service gives an exposure score of "9.6 UNSAFE 😨" for the unhardened service, which as of now we bring down to "1.4 OK 🙂".

I believe there is an issue that may be caused by one (or more) of these directives. When I remove my Yubikey and plug it back in, it stops working until I restart pcscd.service. I then also restart my ssh-agent.service, and then begin using it as normal again. I quickly tested by reverting to no hardening directives, and this does not happen. I might have to spend some time narrowing this down...

All that being said, if there is interest in hardening pcscd.service, I think it would be helpful if others could take a look and test functionality on their systems. I would be happy to fix whatever is needed and submit a pull request once we arrive at something that is stable.

Please let me know if anyone has any thoughts, comments, issues, etc.

I would also like to thank the maintainers and contributors for their work on pcsc-lite.

[1] https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=930530

[2] https://salsa.debian.org/rousseau/PCSC/-/issues/10

[3] https://www.freedesktop.org/software/systemd/man/latest/systemd.exec.html

davidfields commented 3 months ago

When I remove my Yubikey and plug it back in, it stops working until I restart pcscd.service.

I think the culprit for this was PrivateNetwork=yes. After changing it to PrivateNetwork=no, I have not been able to reproduce that problem so far.

there is likely room to further lock down RestrictAddressFamilies=

I replaced RestrictAddressFamilies=~AF_INET AF_INET6 with RestrictAddressFamilies=AF_UNIX AF_NETLINK, which also works for me so far.

LudovicRousseau commented 1 month ago

Sorry for the delay. I missed your messages.

Hardening pcscd is fine. But it may be difficult because pcscd does not know what services are required by the drivers it will load. Some drivers (like https://frankmorgner.github.io/vsmartcard/virtualsmartcard/README.html) will use the network for example.