rootless-containers / slirp4netns

User-mode networking for unprivileged network namespaces
GNU General Public License v2.0
729 stars 82 forks source link

Rootless Docker: Error starting userland proxy: error while calling PortManager.AddPort(): reply.Error: map[desc:bad request: add_hostfwd: slirp_add_hostfwd failed] #251

Closed MarkErik closed 3 years ago

MarkErik commented 3 years ago

I am trying to set up a rootless docker (Ubuntu 20.04) reverse-proxy on port 80/443 that can see the requesting IP address (so that I can write a log file that can be parsed by fail2ban running on the host).

Previously the reverse proxy was running fine in rootless mode by adding the net_bind capability: sudo setcap cap_net_bind_service=ep $HOME/bin/rootlesskit

However I could only see IPs in the log from the Docker VPN network - hence wanting to use slirp4netns.

As non-root user I installed slirp4netns via:

curl -o ~/bin/slirp4netns --fail -L https://github.com/rootless-containers/slirp4netns/releases/download/v1.1.8/slirp4netns-$(uname -m)
chmod +x ~/bin/slirp4netns
sudo setcap cap_net_bind_service=ep $HOME/bin/slirp4netns

I also added the following line to my docker.sevice file (and restarted the services): Environment=DOCKERD_ROOTLESS_ROOTLESSKIT_PORT_DRIVER=slirp4netns

At this point, I would have expected that I would be able to start a container that binds to port 80, but I receive the following error: docker: Error response from daemon: driver failed programming external connectivity on endpoint charming_borg (51676baba5019f688587adf0c79c4a9f9afab3c1661329e04ac4085891a4cf73): Error starting userland proxy: error while calling PortManager.AddPort(): reply.Error: map[desc:bad request: add_hostfwd: slirp_add_hostfwd failed].

I recognise that one option is to lower the unprivileged ports to e.g. 80, but I am wondering why my current approach isn't working. Thank you in advance for any help!

AkihiroSuda commented 3 years ago

Please try net.ipv4.ip_unprivileged_port_start=0

https://rootlesscontaine.rs/getting-started/common/sysctl/

Setcap is not meaningful for slirp4netns because RootlessKit launches slirp4netns in userNS, which discards the cap.