From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mail02.haj.ipfire.org (localhost [IPv6:::1]) by mail02.haj.ipfire.org (Postfix) with ESMTP id 4cZZhK2s9cz2xSN for ; Sun, 28 Sep 2025 19:51:29 +0000 (UTC) Received: from mail01.ipfire.org (mail01.haj.ipfire.org [IPv6:2001:678:b28::25]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange x25519 server-signature ECDSA (secp384r1) server-digest SHA384 client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mail01.haj.ipfire.org", Issuer "R13" (verified OK)) by mail02.haj.ipfire.org (Postfix) with ESMTPS id 4cZZhG0Pz1z2xMD for ; Sun, 28 Sep 2025 19:51:26 +0000 (UTC) Received: from [127.0.0.1] (localhost [127.0.0.1]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange x25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (No client certificate requested) by mail01.ipfire.org (Postfix) with ESMTPSA id 4cZZhB325wz3Gn for ; Sun, 28 Sep 2025 19:51:21 +0000 (UTC) DKIM-Signature: v=1; a=ed25519-sha256; c=relaxed/relaxed; d=ipfire.org; s=202003ed25519; t=1759089085; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=k/fAq2phO+CC+7r8Nh9ORj3Ajg5e54QpMQ6NwcTenqY=; b=RqNHpEf3GnP0nwRufxar+D0W9XloxQteuGtb7oBshNNJBchOVCoZPNM27AsGvyPrYfzyq7 pe15jW/1W2HJ23BA== DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ipfire.org; s=202003rsa; t=1759089085; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=k/fAq2phO+CC+7r8Nh9ORj3Ajg5e54QpMQ6NwcTenqY=; b=QjFsv2oR3u6PLq8m1tBwoZ0jlOhcW/5ctXUvXKL52g+fHybxkgF/hJWcnnac0i2N4MC4Tm SXVrzMsibcmk/9O+/+agZez0yhXvrSQhkipvWgKd265P4/aVn7pmWz/21UvccD8Kci6GPW Fcj0X6QppXQXd5qf3dlmf8GC/u2Dvx/RNr3XWonQGogNaujeoQJ8cUTOx67cMtGq/7K9UX FGLybWwKpkyDmUr/F4m3pwxcDBD9Hm98r0g5j3Xlp9tN0NVRPSq9Vi+GONYcYqhBol1v9w SnnED2X9/AfJCxC2HjmibilcTqMIbTzZ/UUpw3RcJhSZvtuDa77hbNmhAI3a0g== Message-ID: <2dbd27d0-92f5-4611-b7c8-a98185601f0e@ipfire.org> Date: Sun, 28 Sep 2025 19:51:00 +0000 Precedence: list List-Id: List-Subscribe: , List-Unsubscribe: , List-Post: List-Help: Sender: Mail-Followup-To: MIME-Version: 1.0 To: "IPFire: Development" From: =?UTF-8?Q?Peter_M=C3=BCller?= Subject: [PATCH] initscripts: Always wait for xtables lock when running iptables commands Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit If not explicitly instructed to do so, iptables by default aborts with an error message such as > Can't lock /run/xtables.lock: Resource temporarily unavailable > Another app is currently holding the xtables lock. Perhaps you want to use the -w option? if the Xtables lock is still set, i.e., another iptables operation is currently in progress. This causes iptables commands not to be executed at all if there are delays during the boot procedure, e.g. due to slow PPPoE dial-up procedure or similar. To ensure deterministic behavior, this match modifies initscripts to always execute iptables to wait for the Xtables lock to be removed, to make sure iptables rules are installed properly (the "firewall" initscript is doing so already). Fixes: #13896 - OpenVPN RW port not opened in firewall after reboot Signed-off-by: Peter Müller Tested-by: Peter Müller --- src/initscripts/networking/red | 4 ++-- src/initscripts/packages/tor | 10 +++++----- src/initscripts/system/dhcp | 16 ++++++++-------- src/initscripts/system/openvpn-n2n | 10 +++++----- src/initscripts/system/openvpn-rw | 6 +++--- src/initscripts/system/wireguard | 20 ++++++++++---------- 6 files changed, 33 insertions(+), 33 deletions(-) diff --git a/src/initscripts/networking/red b/src/initscripts/networking/red index 6d779b365..536fc972c 100644 --- a/src/initscripts/networking/red +++ b/src/initscripts/networking/red @@ -162,8 +162,8 @@ case "${1}" in elif [ "${TYPE}" == "DHCP" ]; then # Add firewall rules to allow comunication with the dhcp server on red. - iptables -A REDINPUT -p tcp --source-port 67 --destination-port 68 -i ${DEVICE} -j ACCEPT - iptables -A REDINPUT -p udp --source-port 67 --destination-port 68 -i ${DEVICE} -j ACCEPT + iptables --wait -A REDINPUT -p tcp --source-port 67 --destination-port 68 -i ${DEVICE} -j ACCEPT + iptables --wait -A REDINPUT -p udp --source-port 67 --destination-port 68 -i ${DEVICE} -j ACCEPT echo -n "${DEVICE}" > /var/ipfire/red/iface diff --git a/src/initscripts/packages/tor b/src/initscripts/packages/tor index 47797265c..eef9682f3 100644 --- a/src/initscripts/packages/tor +++ b/src/initscripts/packages/tor @@ -37,19 +37,19 @@ function setup_firewall() { # Allow incoming traffic to Tor relay (and directory) port and # all outgoing TCP connections from Tor user. if [ "${TOR_RELAY_ENABLED}" = "on" -a -n "${TOR_RELAY_PORT}" ]; then - iptables -A TOR_INPUT -p tcp --dport "${TOR_RELAY_PORT}" -j ACCEPT - iptables -A TOR_OUTPUT -p tcp -m owner --uid-owner tor -j ACCEPT + iptables --wait -A TOR_INPUT -p tcp --dport "${TOR_RELAY_PORT}" -j ACCEPT + iptables --wait -A TOR_OUTPUT -p tcp -m owner --uid-owner tor -j ACCEPT fi if [ "${TOR_RELAY_ENABLED}" = "on" -a -n "${TOR_RELAY_DIRPORT}" ] && [ "${TOR_RELAY_DIRPORT}" -ne 0 ]; then - iptables -A TOR_INPUT -p tcp --dport "${TOR_RELAY_DIRPORT}" -j ACCEPT + iptables --wait -A TOR_INPUT -p tcp --dport "${TOR_RELAY_DIRPORT}" -j ACCEPT fi } function flush_firewall() { # Flush all rules. - iptables -F TOR_INPUT - iptables -F TOR_OUTPUT + iptables --wait -F TOR_INPUT + iptables --wait -F TOR_OUTPUT } case "${1}" in diff --git a/src/initscripts/system/dhcp b/src/initscripts/system/dhcp index 61b951658..826cd2dfe 100644 --- a/src/initscripts/system/dhcp +++ b/src/initscripts/system/dhcp @@ -28,10 +28,10 @@ eval $(/usr/local/bin/readhash /var/ipfire/ethernet/settings) eval $(/usr/local/bin/readhash /var/ipfire/dhcp/settings) function flush_chains() { - iptables -F DHCPGREENINPUT - iptables -F DHCPGREENOUTPUT - iptables -F DHCPBLUEINPUT - iptables -F DHCPBLUEOUTPUT + iptables --wait -F DHCPGREENINPUT + iptables --wait -F DHCPGREENOUTPUT + iptables --wait -F DHCPBLUEINPUT + iptables --wait -F DHCPBLUEOUTPUT } case "$1" in @@ -41,14 +41,14 @@ case "$1" in if [ -n "${GREEN_DEV}" -a -e "/var/ipfire/dhcp/enable_green" ]; then LISTEN_INTERFACES+=" ${GREEN_DEV}" - iptables -A DHCPGREENINPUT -i "${GREEN_DEV}" -j DHCPINPUT - iptables -A DHCPGREENOUTPUT -o "${GREEN_DEV}" -j DHCPOUTPUT + iptables --wait -A DHCPGREENINPUT -i "${GREEN_DEV}" -j DHCPINPUT + iptables --wait -A DHCPGREENOUTPUT -o "${GREEN_DEV}" -j DHCPOUTPUT fi if [ -n "${BLUE_DEV}" -a -e "/var/ipfire/dhcp/enable_blue" ]; then LISTEN_INTERFACES+=" ${BLUE_DEV}" - iptables -A DHCPBLUEINPUT -i "${BLUE_DEV}" -j DHCPINPUT - iptables -A DHCPBLUEOUTPUT -o "${BLUE_DEV}" -j DHCPOUTPUT + iptables --wait -A DHCPBLUEINPUT -i "${BLUE_DEV}" -j DHCPINPUT + iptables --wait -A DHCPBLUEOUTPUT -o "${BLUE_DEV}" -j DHCPOUTPUT fi boot_mesg "Starting DHCP Server..." diff --git a/src/initscripts/system/openvpn-n2n b/src/initscripts/system/openvpn-n2n index 985398379..f6d554eaf 100644 --- a/src/initscripts/system/openvpn-n2n +++ b/src/initscripts/system/openvpn-n2n @@ -63,10 +63,10 @@ update_firewall_rules() { local local_address # Flush the block chain - iptables -F OVPNBLOCK + iptables --wait -F OVPNBLOCK # Flush the NAT chain - iptables -t nat -F OVPNNAT + iptables --wait -t nat -F OVPNNAT local IFS=',' @@ -85,10 +85,10 @@ update_firewall_rules() { fi # Open port - iptables -A OVPNINPUTN2N -p "${proto}" --dport "${port}" -j ACCEPT + iptables --wait -A OVPNINPUTN2N -p "${proto}" --dport "${port}" -j ACCEPT # Block all communication from transfer networks - iptables -A OVPNBLOCK -s "${transfer_subnet}" -j DROP + iptables --wait -A OVPNBLOCK -s "${transfer_subnet}" -j DROP # Calculate NAT addresses transfer_address="$(calculate_transfer_address "${transfer_subnet}" "${role}")" @@ -96,7 +96,7 @@ update_firewall_rules() { # NAT all outgoing connections away from the transfer net if [ -n "${transfer_address}" -a -n "${local_address}" ]; then - iptables -t nat -A OVPNNAT -s "${transfer_address}" \ + iptables --wait -t nat -A OVPNNAT -s "${transfer_address}" \ -j SNAT --to-source "${local_address}" fi done < /var/ipfire/ovpn/ovpnconfig diff --git a/src/initscripts/system/openvpn-rw b/src/initscripts/system/openvpn-rw index 6359d0d08..d506c8ebd 100644 --- a/src/initscripts/system/openvpn-rw +++ b/src/initscripts/system/openvpn-rw @@ -38,10 +38,10 @@ case "${1}" in modprobe tun &>/dev/null # Flush all firewall rules - iptables -F OVPNINPUTRW + iptables --wait -F OVPNINPUTRW # Open the port - iptables -A OVPNINPUTRW \ + iptables --wait -A OVPNINPUTRW \ -p "${DPROTOCOL}" --dport "${DDEST_PORT}" -j ACCEPT boot_mesg "Starting OpenVPN Roadwarrior Server..." @@ -60,7 +60,7 @@ case "${1}" in killproc /usr/sbin/openvpn # Flush all firewall rules - iptables -F OVPNINPUTRW + iptables --wait -F OVPNINPUTRW ;; restart) diff --git a/src/initscripts/system/wireguard b/src/initscripts/system/wireguard index caaa69cb9..ead1cdce8 100644 --- a/src/initscripts/system/wireguard +++ b/src/initscripts/system/wireguard @@ -216,7 +216,7 @@ generate_config() { ip addr add "${local_address}" dev "${intf}" # Apply MASQUERADE - iptables -t nat -A WGNAT -o "${intf}" -j MASQUERADE + iptables --wait -t nat -A WGNAT -o "${intf}" -j MASQUERADE fi echo "[Interface]" @@ -230,7 +230,7 @@ generate_config() { echo "ListenPort = ${port}" # Open the port - iptables -A WGINPUT -p udp --dport "${port}" -j ACCEPT + iptables --wait -A WGINPUT -p udp --dport "${port}" -j ACCEPT fi echo "[Peer]" @@ -285,7 +285,7 @@ generate_config() { # Set blocking rules for local_subnet in ${local_subnets//|/ }; do for remote_subnet in ${remote_subnets//|/ }; do - iptables -I WGBLOCK \ + iptables --wait -I WGBLOCK \ -s "${remote_subnet}" -d "${local_subnet}" -j RETURN done done @@ -297,23 +297,23 @@ generate_config() { reload_firewall() { # Flush all previous rules - iptables -F WGINPUT - iptables -t nat -F WGNAT + iptables --wait -F WGINPUT + iptables --wait -t nat -F WGNAT if [ "${ENABLED}" = "on" ]; then - iptables -A WGINPUT -p udp --dport "${PORT}" -j ACCEPT + iptables --wait -A WGINPUT -p udp --dport "${PORT}" -j ACCEPT fi - iptables -F WGBLOCK + iptables --wait -F WGBLOCK # Don't block any traffic from Roadwarrior peers if [ -n "${CLIENT_POOL}" ]; then - iptables -A WGBLOCK -s "${CLIENT_POOL}" -i wg0 -j RETURN - iptables -A WGBLOCK -d "${CLIENT_POOL}" -o wg0 -j RETURN + iptables --wait -A WGBLOCK -s "${CLIENT_POOL}" -i wg0 -j RETURN + iptables --wait -A WGBLOCK -d "${CLIENT_POOL}" -o wg0 -j RETURN fi # Block all other traffic - iptables -A WGBLOCK -j REJECT --reject-with icmp-admin-prohibited + iptables --wait -A WGBLOCK -j REJECT --reject-with icmp-admin-prohibited # Flush any custom routes ip route flush table wg 2>/dev/null -- 2.51.0