Podman pod briefly available, then unreachable

Hi there,

I'm trying to get some containers running on my Linksys WRT3200ACM running OpenWrt 23.05.5, r24106-10cc5fcd00. Due to the nftables/iptables incompatibility with Docker, I decided to try my luck at podman. I followed the guide at https://openwrt.org/docs/guide-user/virtualization/docker_host to no avail. Then, I tried the configuration outlined by oskarirauta here - https://github.com/openwrt/packages/issues/22255#issuecomment-1743827579 .

Suddenly this worked - I could ping my pod's IP, and even curl the nginx container I'd spun up. However, literally a few seconds later, when I issued another curl command, the pod was unreachable. Here is a console log:

BusyBox v1.36.1 (2024-09-23 12:34:46 UTC) built-in shell (ash)

  _______                     ________        __
 |       |.-----.-----.-----.|  |  |  |.----.|  |_
 |   -   ||  _  |  -__|     ||  |  |  ||   _||   _|
 |_______||   __|_____|__|__||________||__|  |____|
          |__| W I R E L E S S   F R E E D O M
 -----------------------------------------------------
 OpenWrt 23.05.5, r24106-10cc5fcd00
 -----------------------------------------------------
root@OpenWrt:~# podman pod ls
POD ID        NAME        STATUS      CREATED         INFRA ID      # OF CONTAINERS
a8bbce7cacba  navi        Exited      55 minutes ago  e0957f004f73  2
root@OpenWrt:~# podman pod rm navi
a8bbce7cacbadccdf7d4c08f72df4b3e1d6a4389fe715e0e0e969a0618124650
root@OpenWrt:~# podman pod create --replace --name navi  --hostname navi --ip 10.129.0.2
5d064b457bf111bda67a82197162955e75d59cfa2d2222a10425e2c9bdd0e6a3
root@OpenWrt:~# podman create --name navi --pod navi --replace --systemd false nginx
99aac83e5dfed9e72346fc43455d4749b32a700d5ce5f1da53af74eeb9017dd5
root@OpenWrt:~# podman pod start navi
5d064b457bf111bda67a82197162955e75d59cfa2d2222a10425e2c9bdd0e6a3
root@OpenWrt:~# podman pod ls
POD ID        NAME        STATUS      CREATED         INFRA ID      # OF CONTAINERS
5d064b457bf1  navi        Running     20 seconds ago  0532f5422503  2
root@OpenWrt:~# ping 10.129.0.2
PING 10.129.0.2 (10.129.0.2): 56 data bytes
64 bytes from 10.129.0.2: seq=0 ttl=64 time=0.165 ms
64 bytes from 10.129.0.2: seq=1 ttl=64 time=0.081 ms
64 bytes from 10.129.0.2: seq=2 ttl=64 time=0.084 ms
64 bytes from 10.129.0.2: seq=3 ttl=64 time=0.083 ms
64 bytes from 10.129.0.2: seq=4 ttl=64 time=0.088 ms
64 bytes from 10.129.0.2: seq=5 ttl=64 time=0.073 ms
64 bytes from 10.129.0.2: seq=6 ttl=64 time=0.075 ms
64 bytes from 10.129.0.2: seq=7 ttl=64 time=0.071 ms
^C
--- 10.129.0.2 ping statistics ---
8 packets transmitted, 8 packets received, 0% packet loss
round-trip min/avg/max = 0.071/0.090/0.165 ms
root@OpenWrt:~# curl http://10.129.0.2
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
<style>
html { color-scheme: light dark; }
body { width: 35em; margin: 0 auto;
font-family: Tahoma, Verdana, Arial, sans-serif; }
</style>
</head>
<body>
<h1>Welcome to nginx!</h1>
<p>If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.</p>

<p>For online documentation and support please refer to
<a href="http://nginx.org/">nginx.org</a>.<br/>
Commercial support is available at
<a href="http://nginx.com/">nginx.com</a>.</p>

<p><em>Thank you for using nginx.</em></p>
</body>
</html>
root@OpenWrt:~# curl http://10.129.0.2
^C
root@OpenWrt:~# ping 10.129.0.2
PING 10.129.0.2 (10.129.0.2): 56 data bytes
^C
--- 10.129.0.2 ping statistics ---
6 packets transmitted, 0 packets received, 100% packet loss
root@OpenWrt:~# podman pod ls
POD ID        NAME        STATUS      CREATED        INFRA ID      # OF CONTAINERS
5d064b457bf1  navi        Running     2 minutes ago  0532f5422503  2
root@OpenWrt:~# podman pod restart navi
5d064b457bf111bda67a82197162955e75d59cfa2d2222a10425e2c9bdd0e6a3
root@OpenWrt:~# ping 10.129.0.2
PING 10.129.0.2 (10.129.0.2): 56 data bytes
^C
--- 10.129.0.2 ping statistics ---
5 packets transmitted, 0 packets received, 100% packet loss
root@OpenWrt:~#

Here are the config files. I've only made some slight adjustments to e.g. block traffic from wan to the podman zone:

root@OpenWrt:~# cat /etc/containers/networks/podman.json
{
     "name": "podman",
     "id": "5ef894788befd4d42498314b6e66282ca730aa2e1e82f9b9597bf4d1725ca074",
     "driver": "bridge",
     "network_interface": "podman0",
     "created": "2023-02-20T08:56:34.652030952Z",
     "subnets": [
          {
               "subnet": "10.129.0.0/24",
               "gateway": "10.129.0.1"
          }
     ],
     "ipv6_enabled": false,
     "internal": false,
     "dns_enabled": true,
     "ipam_options": {
          "driver": "host-local"
     }
}
root@OpenWrt:~# cat /etc/config/network

config interface 'loopback'
	option device 'lo'
	option proto 'static'
	option ipaddr '127.0.0.1'
	option netmask '255.0.0.0'

config globals 'globals'
	option ula_prefix 'fddb:4e9a:26d6::/48'

config device
	option name 'br-lan'
	option type 'bridge'
	list ports 'lan1'
	list ports 'lan2'
	list ports 'lan3'
	list ports 'lan4'

config interface 'lan'
	option device 'br-lan'
	option proto 'static'
	option netmask '255.255.255.0'
	option ip6assign '60'
	list dns '8.8.8.8'
	option ipaddr '192.168.2.1'

config device
	option name 'wan'
	option macaddr '32:23:03:dc:1c:18'

config interface 'wwan'
	option proto 'dhcp'
	option device 'phy1-sta0'

config interface 'repeater_bridge'
	option proto 'relay'
	option ipaddr '192.168.1.10'
	list network 'lan'
	list network 'wwan'


config interface 'podman0'
	option proto 'cni'
	option device 'podman0'
	option target '10.129.0.0/24'
	option gateway '10.129.0.1'
	option source '10.100.0.1'
	option disabled '1'
root@OpenWrt:~# cat /etc/hotplug.d/10-cni
#!/bin/sh
[ $(uci get network.${INTERFACE}.proto) = "cni" ] && {
	[ "$ACTION" = add ] && ifup ${INTERFACE}
	[ "$ACTION" = remove ] && ifdown ${INTERFACE}
	[ "$ACTION" = change ] && {
		ifdown ${INTERFACE}
		sleep 1
		ifup ${INTERFACE}
	}
}
root@OpenWrt:~# cat /etc/config/firewall

config defaults
	option input 'ACCEPT'
	option output 'ACCEPT'
	option forward 'REJECT'
	option synflood_protect '1'

config zone
	option name 'lan'
	option input 'ACCEPT'
	option output 'ACCEPT'
	option forward 'ACCEPT'
	list network 'lan'
	list network 'wwan'


config zone
	option name		podman
	list network		'podman0'
	option input		REJECT
	option output		ACCEPT
	option forward		ACCEPT
	option mtu_fix		1

config forwarding
	option src		lan
	option dest		podman

config forwarding
	option src		podman
	option dest		wan

#config forwarding
#	option src		wan
#	option dest		podman

config rule
	option name 'Allow-Podman-DNS'
	option src 'podman'
	list dest_ip '10.129.0.1'
	option dest_port '53'
	option target 'ACCEPT'
root@OpenWrt:~#

Does anyone know what could be causing this strange behaviour? I'd be very grateful for any kind of support. Thanks!

I've just been able to reproduce the behaviour. What I did:

  • In /etc/config/firewall , changed the podman zone's input rule from a default of REJECT to a default ACCEPT - just to see if that was causing the problem
  • reboot
  • start the pod and ping it

Result after 13 pings, the connectivity broke down:

root@OpenWrt:/mnt/flashdrive# podman pod start navi ; ping 10.129.0.2
5d064b457bf111bda67a82197162955e75d59cfa2d2222a10425e2c9bdd0e6a3
PING 10.129.0.2 (10.129.0.2): 56 data bytes
64 bytes from 10.129.0.2: seq=0 ttl=64 time=0.250 ms
64 bytes from 10.129.0.2: seq=1 ttl=64 time=0.085 ms
64 bytes from 10.129.0.2: seq=2 ttl=64 time=0.086 ms
64 bytes from 10.129.0.2: seq=3 ttl=64 time=0.080 ms
64 bytes from 10.129.0.2: seq=4 ttl=64 time=0.085 ms
64 bytes from 10.129.0.2: seq=5 ttl=64 time=0.085 ms
64 bytes from 10.129.0.2: seq=6 ttl=64 time=0.094 ms
64 bytes from 10.129.0.2: seq=7 ttl=64 time=0.081 ms
64 bytes from 10.129.0.2: seq=8 ttl=64 time=0.085 ms
64 bytes from 10.129.0.2: seq=9 ttl=64 time=0.087 ms
64 bytes from 10.129.0.2: seq=10 ttl=64 time=0.098 ms
64 bytes from 10.129.0.2: seq=11 ttl=64 time=0.085 ms
64 bytes from 10.129.0.2: seq=12 ttl=64 time=0.078 ms
^C
--- 10.129.0.2 ping statistics ---
24 packets transmitted, 13 packets received, 45% packet loss
round-trip min/avg/max = 0.078/0.098/0.250 ms
root@OpenWrt:/mnt/flashdrive#

No need to reboot on firewall changes. Just call service firewall reload

Did you check the log of the pod / container if it tells you something? And system log?

Just out of curiosity because I also managed to setup podman on openwrt, is there any particular reason you chose to run a pod instead of separate containers?

@totkeks - nothing surprising in the container logs:

root@OpenWrt:~# podman logs -f navi
/docker-entrypoint.sh: /docker-entrypoint.d/ is not empty, will attempt to perform configuration
ERRO[0000] Waiting for container to exit: cannot read events with the "none" backend
/docker-entrypoint.sh: Looking for shell scripts in /docker-entrypoint.d/
/docker-entrypoint.sh: Launching /docker-entrypoint.d/10-listen-on-ipv6-by-default.sh
10-listen-on-ipv6-by-default.sh: info: Getting the checksum of /etc/nginx/conf.d/default.conf
10-listen-on-ipv6-by-default.sh: info: Enabled listen on IPv6 in /etc/nginx/conf.d/default.conf
/docker-entrypoint.sh: Sourcing /docker-entrypoint.d/15-local-resolvers.envsh
/docker-entrypoint.sh: Launching /docker-entrypoint.d/20-envsubst-on-templates.sh
/docker-entrypoint.sh: Launching /docker-entrypoint.d/30-tune-worker-processes.sh
/docker-entrypoint.sh: Configuration complete; ready for start up
2025/01/04 19:43:13 [notice] 1#1: using the "epoll" event method
2025/01/04 19:43:13 [notice] 1#1: nginx/1.27.3
2025/01/04 19:43:13 [notice] 1#1: built by gcc 12.2.0 (Debian 12.2.0-14)
2025/01/04 19:43:13 [notice] 1#1: OS: Linux 5.15.167
2025/01/04 19:43:13 [notice] 1#1: getrlimit(RLIMIT_NOFILE): 1048576:1048576
2025/01/04 19:43:13 [notice] 1#1: start worker processes
2025/01/04 19:43:13 [notice] 1#1: start worker process 24
2025/01/04 19:43:13 [notice] 1#1: start worker process 25
10.129.0.1 - - [04/Jan/2025:19:43:34 +0000] "GET / HTTP/1.1" 200 615 "-" "curl/8.7.1" "-"
2025/01/04 19:45:57 [notice] 1#1: signal 3 (SIGQUIT) received, shutting down
2025/01/04 19:45:57 [notice] 24#24: gracefully shutting down
2025/01/04 19:45:57 [notice] 25#25: gracefully shutting down
2025/01/04 19:45:57 [notice] 24#24: exiting
2025/01/04 19:45:57 [notice] 25#25: exiting
2025/01/04 19:45:57 [notice] 24#24: exit
2025/01/04 19:45:57 [notice] 25#25: exit
2025/01/04 19:45:57 [notice] 1#1: signal 17 (SIGCHLD) received from 25
2025/01/04 19:45:57 [notice] 1#1: worker process 24 exited with code 0
2025/01/04 19:45:57 [notice] 1#1: worker process 25 exited with code 0
2025/01/04 19:45:57 [notice] 1#1: exit

I didn't really choose to run a pod instead of 'vanilla' containers, I just have 0 podman experience and was trying to follow the guides as closely as possible in order to get everything working first of all. I guess being able to specify a fixed IP is handy for debugging, especially when communication with the pod isn't stable.

But in any event, when I run a container normally (e.g. podman run -p 8081:80 nginx), get its IP (podman inspect containername) and then try to ping/connect to the IP, I can't either.

Any ideas? How did you set up your system?

Here is the container config

This auto assign DNS names to the pods

This is the network for the containers

And this is work in progress init service script to run containers automatically based on uci config for containers.

So far networking between containers worked. And also reaching the containers from the router as well machines in the private lan.

The podman version in 23.05 is pretty old, you could try 24.10 (incl. podman 5.2.2) and the podman guide

https://openwrt.org/docs/guide-user/virtualization/docker_host?s[]=podman#podman

@totkeks - thanks for the configs! I'll have a proper look at them tomorrow.

@kirdes - okay, if all else fails, I'll upgrade to 24.10. Unfortunately the upgrade process here is rather laborious, so I'd rather avoid if it I can.

Just wanted to post another update here - I didn't do anything with it for the past few hours, just left my router running. I logged into my router just now, and could ping & curl the pod. A few minutes later, and it's still reachable. No idea why it's decided to behave itself.

One strange thing:

the podman0 interface is disabled in your config.

I`d try enabling the interface and see if it helps.

Yup, that jumped out at me too when I was copying it from https://github.com/openwrt/packages/issues/22255#issuecomment-1743827579 , but I decided to stick with it for the time being at least - especially since I was at least having intermittent connectivity.

I've set it to '0' now. After service network reload and podman pod stop navi ; podman pod start navi , I'm able to ping and curl the pod for a while, then it becomes unresponsive, even though podman pod ls still lists it as Running. I wait another while, and it suddenly becomes responsive again. :man_shrugging:

I'm beginning to think it might be worthwhile to first upgrade to 24.10 before debugging further :confused:

So, I bit the bullet and upgraded OpenWRT. Now on OpenWrt 24.10.0-rc5 r28304-6dacba30a7 / LuCI openwrt-24.10 branch 25.002.60082~f001a35.

Installed conmon crun catatonit netavark podman external-protocol.

With my old podman/networking configs still in place, I did:

podman pod create --replace --name navi  --hostname navi --ip 10.129.0.2 && \
podman pod start navi && \
podman create --name navi --pod navi --replace --systemd false nginx

This complained that iptables was not available, which I then installed. Then it complained that ip6tables wasn't available, which I installed. Now it complains about a kernel module not being loaded, but I'm unsure which kernel module I should be installing and loading in order to enable masquerading for iptables:

root@OpenWrt:/mnt# podman pod create --replace --name navi  --hostname navi --ip 10.129.0.2 && \
> podman pod start navi && \
> podman create --name navi --pod navi --replace --systemd false nginx
df7bdc5073412e2c01624f2a1ea34bec3bae7fbfeeda15ece4b19834f799a051
Error: starting container f0f0639735ffeb9605b98d19caa012f814d9f847439f759d530d42e57b9ec4d4: netavark: unable to append rule '! -d 224.0.0.0/4 -j MASQUERADE' to table 'nat': code: 4, msg: Warning: Extension MASQUERADE revision 0 not supported, missing kernel module?
iptables v1.8.10 (nf_tables):  RULE_APPEND failed (No such file or directory): rule in chain NETAVARK-1D8721804F16F

Any idea? And should this be happening? I wasn't aware of having iptables installed on my old openwrt setup, and yet it wasn't complaining about it, so I'm wondering about that..

You need to disable the netavark firewall driver in /etc/containers/containers.conf (the guide is outdated here)

firewall_driver = "none"

Then setup the needed firewall rules through the OpenWrt firewall as described in the guide.

1 Like

That did the trick - many thanks! And thanks for your and @totkeks ' support in this thread, it's been much appreciated!

I can now get the pod up and running, and it's reachable. I'll leave it running for a while, do some tests, and see if it suffers the same strange periodic disconnections as on the old openwrt version. Hopefully all is now fixed, though.

1 Like

Having monitored things, I can confirm that pods are running reliably now and can be pinged and curled from the router's shell reliably. Thanks again!

I tried to make the pod accessible from my LAN last night to not much success. I tried this a number of ways -

  • port forwarding: I set up a port forwarding, pointing the port 8080 on the router to point to port 80 on the pod's IP 10.129.0.2:
config redirect
        option dest 'podman'
        option target 'DNAT'
        option name 'navitest'
        option src 'lan'
        option src_dport '8080'
        option dest_ip '10.129.0.2'
        option dest_port '80'

This didn't work - the port wasn't opened (I'd clicked "Save & Apply" on LuCI, so expected it to take immediate effect):

root@OpenWrt:~# curl http://localhost:8080
curl: (7) Failed to connect to localhost port 8080 after 0 ms: Error
root@OpenWrt:~# nano /etc/config/firewall
root@OpenWrt:~# telnet localhost 8080
Trying ::1...
telnet: connect to address ::1: Connection refused
Trying 127.0.0.1...
telnet: connect to address 127.0.0.1: Connection refused
root@OpenWrt:~#
  • Then I tried to bridge the local network and the podman's 10.129.x.x network to make these pod IPs accessible from other computers on the network. This would be my favoured solution, as it seems cleanest, but this didn't work:
config rule
        option name 'navitest'
        option src '*'
        option dest 'podman'
        list dest_ip '10.129.0.2'
        option target 'ACCEPT'
  • I then figured it might be an idea to dump pods altogether and just try a normal container -> 0.0.0.0 port forward. I ran podman run -d -p 8080:80 nginx and then tried to curl this port. It didn't work, however, the port was definitely open:
root@OpenWrt:~# podman run -d -p 8080:80 nginx
f4775ed7b05d23869a9187725d7a49ea37da4ad44729deb81212b03acb479b4c
root@OpenWrt:~# podman ps
CONTAINER ID  IMAGE                                    COMMAND               CREATED         STATUS         PORTS                         NAMES
e5b4f5c9fa7b  localhost/podman-pause:5.2.2-1736517479                        38 seconds ago  Up 38 seconds                                8ba2b3cdba00-infra
cf22f8b3b00f  docker.io/library/nginx:latest           nginx -g daemon o...  38 seconds ago  Up 38 seconds                                navi
f4775ed7b05d  docker.io/library/nginx:latest           nginx -g daemon o...  2 seconds ago   Up 2 seconds   0.0.0.0:8080->80/tcp, 80/tcp  boring_lovelace
root@OpenWrt:~# curl http://localhost:8080
^C
root@OpenWrt:~# telnet localhost 8080
Trying ::1...
telnet: connect to address ::1: Connection refused
Trying 127.0.0.1...
Connected to localhost.
Escape character is '^]'.
GET /


hello


^]

quit
telnet> Connection closed.
root@OpenWrt:~#

Any idea what I'm missing / screwing up here?

For reference, here's the /etc/config/firewall before any modifications:


config defaults
	option input 'ACCEPT'
	option output 'ACCEPT'
	option forward 'REJECT'
	option synflood_protect '1'

config zone
	option name 'lan'
	option input 'ACCEPT'
	option output 'ACCEPT'
	option forward 'ACCEPT'
	list network 'lan'
	list network 'repeater_bridge'
	list network 'wwan'

config zone
	option name 'podman'
	list network 'podman0'
	option input 'ACCEPT'
	option output 'ACCEPT'
	option forward 'ACCEPT'
	option mtu_fix '1'

config forwarding
	option src 'lan'
	option dest 'podman'

config forwarding
	option src 'podman'
	option dest 'wan'

config rule
	option name 'Allow-Podman-DNS'
	option src 'podman'
	list dest_ip '10.129.0.1'
	option dest_port '53'
	option target 'ACCEPT'

As always, I'm very grateful for any and all help. Thanks.

The redirect rule looks good to me. Can you check that from a client that is actually connected to LAN?
I might be wrong, but connecting from within the router does not apply as LAN zone traffic and consequently the rule does not apply.

And the forwarding rule from the guide

config forwarding
	option src 'lan'
	option dest 'podman'

should be enough to connect to podman containers.

Your rule with source "*" would also apply for WAN, is this was you actually want to do?

I would recommend my solution again as it has proven to work.

Containers have their own subnet on a bridge and zone in the firewall.

DNS entries are updated via the hotplug script.

Then you can just reach your containers by the names given to them. Either the short one, grafana, influxdb or the full local domain name.

The issue with pods sharing the same IP is that you can't bind to port 80 twice. Which is why I prefer individual containers. Each gets a veth by podman, which then gets an IP and a DNS name. Then I don't have to run grafana on port 5000whatever, because every service has a name.

There is another route by using a reverse proxy on the router, so that all requests for those dns names go to the router and the reverse proxy forwards the requests to the correct IPs and ports in the container network. I don't like this though. too much overhead in an anyway small router.