== My wish for per-port IP access controls in systemd .service units [[I tweeted https://twitter.com/thatcks/status/1530346596361199618]]: > I wish systemd offered a simple way to say 'only allow the following > IP ranges to connect to port X of this service'. You can allow only > some IP ranges, but then that applies to outgoing connections too and > things like DNS queries done by the service. > > [...] > > There are lots of general Linux options to firewall access to a port, > but AFAIK none of them are easily tied to a .service unit so that you > always get the two together and can't deploy & activate the service > without its firewall protection. Suppose, not entirely hypothetically, that you need to deploy an instance of [[Prometheus Blackbox https://github.com/prometheus/blackbox_exporter]] on some host in order to let [[your Prometheus setup ../sysadmin/PrometheusGrafanaSetup-2019]] see a network segment that it isn't normally connected to. [[It's not entirely safe to allow everyone inside your network to talk to Blackbox ../sysadmin/PrometheusBlackboxAccessRisk]], which means that you want to restrict access to the port it listens on. Systemd offers [[_IPAddressAllow_ and _IPAddressDeny_ https://www.freedesktop.org/software/systemd/man/systemd.resource-control.html#IPAddressAllow=ADDRESS%5B/PREFIXLENGTH%5D%E2%80%A6]] as part of [[its general resource control https://www.freedesktop.org/software/systemd/man/systemd.resource-control.html]], but when applied to .service units they affect all network activity performed by the service, not just connections to it. Since the purpose of Blackbox is to send network traffic to external things, you have to allow at least everything it needs to probe to talk to Blackbox, which may be less than ideal. You can write firewall rules, but currently there's nothing that embeds firewall rules in systemd service units or ties the two together so that you can't deploy the service without the firewall. Well, I suppose you can add some [[_ExecStartPre_ https://www.freedesktop.org/software/systemd/man/systemd.service.html#ExecStartPre=]] commands (and the corresponding [[_ExecStopPost_ https://www.freedesktop.org/software/systemd/man/systemd.service.html#ExecStopPost=]]), but that gets awkward and it may not interact well with any other uses of Linux firewalling you're doing on the system. At the very least it feels like a hack, and it's not naturally modular the way that systemd .service units normally are, where you don't have to care about what other ones do. According to the systemd documentation, you can do this if you use a .socket unit (with IP address restrictions on the socket unit but not the service unit). Unfortunately, not many things support systemd socket activation (and Blackbox isn't one of them). Also, I'm not sure how well a socket unit and socket activation works in general for socket services that are daemons and keep running forever. (It's possible that [[firewalld https://firewalld.org/]] will someday be sufficiently pervasive that it can serve as the general, modular IP access control system for things like that. This would allow more confidence that your .service manual firewall changes wouldn't collide with or be wiped out by something that another service was doing.)