OpenVPN server fails to respond to clients after outgoing interface is removed and re-created
Nobody has claimed this yet.
- Dominant language
- C
- Stars
- 14.6k
- Forks
- 3.4k
- PR merge metrics
- No merged PRs in 30d
Description
Description
While operating OpenVPN client and server over UDP, the outgoing interface in server was restarted. It was a tunnel device that was removed and re-created. Consequently, when the client sent packets to the server, these were received. However the server was unable to send packets to client, reporting an error to its log:
Beta/10.10.1.22:33192 write UDPv4 []: No such device (fd=6,code=19)
The tunnel was inoperable until the client initiated reconnection (via keepalive).
If the restart of interface happened in the client, it had no ill effects.
Reproduction
- Create OpenVPN tunnel between 2 devices over some dynamically created interface in the server. For example WiFi.
- Test the connection over the tunnel. It should work.
- Destroy and re-create the interface (turn-off WiFi, then turn it on). The interface must be destroyed, not just closed (DOWN).
- Test the connection to client and the connection over the tunnel. The connection to the client will be working but the connection over the tunnel will not.
Expected behavior
- The server should be able to send packets when there is a valid route to a client.
Version information
OS: Linux-6.1.18 (embedded)
OpenVPN: 2.6.5
Snippet from config.log (cross-compilation)
$ /usr/src/racom/ra2_fwbuild/build/openvpn/src/configure --host=mips64-linux-gnuabi64 --prefix= --sysconfdir=/etc --with-sysroot=/usr/src/racom/ra2_fwbuild/staging --disable-dependency-tracking --disable-selinux --disable-systemd --disable-plugins --disable-debug --disable-pkcs11 --enable-small IFCONFIG= ROUTE= IPROUTE=/sbin/ip NETSTAT=/bin/netstat
hostname = lapka-Latitude-5520
uname -m = x86_64
uname -r = 6.2.0-33-generic
uname -s = Linux
uname -v = #33-Ubuntu SMP PREEMPT_DYNAMIC Tue Sep 5 14:49:19 UTC 2023
Analysis
When using UDP and compiled with flag ENABLE_IP_PKTINFO, the server stores information about the target address the client used to connect and the index of the interface it used (in_pktinfo::ipi_ifindex in structure link_socket_actual). These are then used to set source address of UDP packets sent to the client (src/openvpn/socket.c: link_socket_write_udp_posix_sendmsg()). However if the interface was removed and re-created, its original index is no longer valid and an attempt to use it leads to the error ("write UDPv4 []: No such device").
Proposed solution
Do not use possibly obsolete ipi_ifindex as a hint for source address resolution. In function src/openvpn/socket.c: link_socket_write_udp_posix_sendmsg() use special value 0 when filling in_pktinfo::ipi_ifindex in CMSG structure for sendmsg().
Tested patch is in attachment.
Alternative solution: Update interface index and stored address with each packet received from client. It may still lead to the error if no new packet from client arrives after the restart of interface.
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start in src/openvpn/socket.c at link_socket_write_udp_posix_sendmsg() and review how ENABLE_IP_PKTINFO stores and uses in_pktinfo::ipi_ifindex. Reproduce the interface removal and recreation scenario described in the issue, then verify that the server can send packets to the client without requiring reconnection.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- c, linux
- Domain
- networking
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Stale
- Clarity
- Clearly specified
- Newbie friendliness
- 45/100