From patchwork Tue Feb 25 09:48:06 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "d12fk (Code Review)" X-Patchwork-Id: 4157 Return-Path: Delivered-To: patchwork@openvpn.net Received: by 2002:a05:7000:a117:b0:5e7:b9eb:58e8 with SMTP id cp23csp71136mab; Tue, 25 Feb 2025 01:48:32 -0800 (PST) X-Forwarded-Encrypted: i=2; AJvYcCWSrjrxn/NbSWDmEwXRIUX7EW+LZTTFnHtgvGGEgwhfefRh6EOrWwsvKTUTWUGiOAuhT7xcf9DZf+0=@openvpn.net X-Google-Smtp-Source: AGHT+IGQPrgZrNeEu2VAftiuEcvbJ0EdnM9YHl2pFf8XvhkrrXxu8PaJSHbUHA9zKJsFUQUlxV1o X-Received: by 2002:a05:6e02:1aab:b0:3cf:ba5:1ea3 with SMTP id e9e14a558f8ab-3d2fc0d3910mr25779885ab.7.1740476912291; Tue, 25 Feb 2025 01:48:32 -0800 (PST) ARC-Seal: i=1; a=rsa-sha256; t=1740476912; cv=none; d=google.com; s=arc-20240605; b=hf5QkPG44JNDR5EcwsEt2MXgE+XvzPE82EKOgEQjQIGuWFxGJApD24YFCTyHnRyKFB ajATfhafGbo/q2VISdmQ3/ZWTNDABQunZZTBZziBcJyTlFXTul/L7OMsuqhcJyVdnRbz yNkvF6+YT+CMpXjRS0ZO2IyK8fqG63Gw/jOns+DW4fzu+a90buQvRvt0mHwXD2tK7QWd BmzvPe7dRJLYNFMhf/pv6KyJWFaKymLiyejimvMV/XEQLy4lZaMbXu9akvToDsOY/eKa 02umJdI8ad6UcETEkIhB490xKZy+f/AfTDpjB8kc/v3GGzhq+YFmBWTpQbE7q6uoHore P/7Q== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=errors-to:cc:reply-to:list-subscribe:list-help:list-post :list-archive:list-unsubscribe:list-id:precedence:subject:user-agent :mime-version:message-id:references:auto-submitted:to:date:from :dkim-signature:dkim-signature:dkim-signature; bh=bYggScmnt0+zAuDOIIHFUgU2Ah1vzgsujRwfyliwWrE=; fh=U7wEyxtwz2o5+UdevFSA47vNeG9knhWH0KV//QhD5a0=; b=ZpRv1pXGcUkn/8edkU1bKketMZzORPbklKeWI0WghnYSAvq24E4aLklvq3PW9HS3MF D0QLgvvmbsk6PAIv4XI/hZ9pPzE8nOTZj986U7xqrLbVRIoW6knSH3Md/8bBrSD0WmEU 0v7rpP8oIvP7AF+JgpPxPS1A9iUBgOoHhA21IgM7DVfl4r8WzwybIuPYbUwEVHKS63dt KkMbgLg5k9UngtaYiH/ry1Iy0YVUNCQ161NIsegfrAZhVtHBwk8h7aUjecFdWeUVXd2J hpCVBbwXcvrdEafe8nEtzBQm3g4Y8llpIfGeCJUCOVfuxYMLkggZ/BL2zblDsVAZTrxN YJag==; dara=google.com ARC-Authentication-Results: i=1; mx.google.com; dkim=neutral (body hash did not verify) header.i=@sourceforge.net header.s=x header.b=m0aMdqJc; dkim=neutral (body hash did not verify) header.i=@sf.net header.s=x header.b=Ozy9odtC; dkim=neutral (body hash did not verify) header.i=@openvpn.net header.s=google header.b=YkXOVdp2; spf=pass (google.com: domain of openvpn-devel-bounces@lists.sourceforge.net designates 216.105.38.7 as permitted sender) smtp.mailfrom=openvpn-devel-bounces@lists.sourceforge.net; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=openvpn.net; dara=fail header.i=@openvpn.net Received: from lists.sourceforge.net (lists.sourceforge.net. [216.105.38.7]) by mx.google.com with ESMTPS id e9e14a558f8ab-3d361ca683asi8801065ab.100.2025.02.25.01.48.31 (version=TLS1_2 cipher=ECDHE-ECDSA-AES128-GCM-SHA256 bits=128/128); Tue, 25 Feb 2025 01:48:32 -0800 (PST) Received-SPF: pass (google.com: domain of openvpn-devel-bounces@lists.sourceforge.net designates 216.105.38.7 as permitted sender) client-ip=216.105.38.7; Authentication-Results: mx.google.com; dkim=neutral (body hash did not verify) header.i=@sourceforge.net header.s=x header.b=m0aMdqJc; dkim=neutral (body hash did not verify) header.i=@sf.net header.s=x header.b=Ozy9odtC; dkim=neutral (body hash did not verify) header.i=@openvpn.net header.s=google header.b=YkXOVdp2; spf=pass (google.com: domain of openvpn-devel-bounces@lists.sourceforge.net designates 216.105.38.7 as permitted sender) smtp.mailfrom=openvpn-devel-bounces@lists.sourceforge.net; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=openvpn.net; dara=fail header.i=@openvpn.net Received: from [127.0.0.1] (helo=sfs-ml-3.v29.lw.sourceforge.com) by sfs-ml-3.v29.lw.sourceforge.com with esmtp (Exim 4.95) (envelope-from ) id 1tmrY7-0003o4-GP; Tue, 25 Feb 2025 09:48:22 +0000 Received: from [172.30.29.66] (helo=mx.sourceforge.net) by sfs-ml-3.v29.lw.sourceforge.com with esmtps (TLS1.2) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.95) (envelope-from ) id 1tmrY6-0003ny-Av for openvpn-devel@lists.sourceforge.net; Tue, 25 Feb 2025 09:48:21 +0000 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=sourceforge.net; s=x; h=Content-Type:Content-Transfer-Encoding:MIME-Version :Message-ID:Reply-To:References:Subject:List-Unsubscribe:List-Id:Cc:To:Date: From:Sender:Content-ID:Content-Description:Resent-Date:Resent-From: Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:In-Reply-To:List-Help: List-Subscribe:List-Post:List-Owner:List-Archive; bh=BNmCwX4fn4XtzbC1Drc08TBjvFTBySBf31V4g3wrOcI=; b=m0aMdqJcuwkeYABhlW+AuIxW4B yHegOwuIRUQgmYLHmhjtTp5S17adG97KPZU4wYz//BzkANfkgYZeWmsnm7IG1qmGNlqiz3SRLtMFS jO74KHTLuA+N/PcGlJhXCYZ7D7sxIRx3KO3IU/VKd9yosNyZ3h2Y2gVfXbx0/iD8HEDs=; DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=sf.net; s=x ; h=Content-Type:Content-Transfer-Encoding:MIME-Version:Message-ID:Reply-To: References:Subject:List-Unsubscribe:List-Id:Cc:To:Date:From:Sender:Content-ID :Content-Description:Resent-Date:Resent-From:Resent-Sender:Resent-To: Resent-Cc:Resent-Message-ID:In-Reply-To:List-Help:List-Subscribe:List-Post: List-Owner:List-Archive; bh=BNmCwX4fn4XtzbC1Drc08TBjvFTBySBf31V4g3wrOcI=; b=O zy9odtCZUFKTQrnc5M0vB3FnYeyEj2QjbDZIkmGha0AKTUn1Y3Wk5KGGLf/qMgQCWkwlDMV7bSJyC 6Rtuqxi7cbVMOCbt3spgKlWPeeEbPeCVpMCcISsfJrmmOqu4CDILABPY69M5Idjctn5CqLr3j3zzL S4SZX9eGgZymnXjY=; Received: from mail-wr1-f41.google.com ([209.85.221.41]) by sfi-mx-2.v28.lw.sourceforge.com with esmtps (TLS1.2:ECDHE-RSA-AES128-GCM-SHA256:128) (Exim 4.95) id 1tmrY3-0008CS-Nd for openvpn-devel@lists.sourceforge.net; Tue, 25 Feb 2025 09:48:21 +0000 Received: by mail-wr1-f41.google.com with SMTP id ffacd0b85a97d-38f325dd9e6so2768395f8f.1 for ; Tue, 25 Feb 2025 01:48:19 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=openvpn.net; s=google; t=1740476888; x=1741081688; darn=lists.sourceforge.net; h=user-agent:content-disposition:content-transfer-encoding :mime-version:message-id:reply-to:references:subject :list-unsubscribe:list-id:auto-submitted:cc:to:date:from:from:to:cc :subject:date:message-id:reply-to; bh=BNmCwX4fn4XtzbC1Drc08TBjvFTBySBf31V4g3wrOcI=; b=YkXOVdp26TJN7WvANjkCw1nN9uKuevILta1qr/uZAFyFq10xbm15lIpGqs1XprtMhl pEJJlUo0+9Heb7Mty0Rd3HuQOpKu2FY4LfzhrEkm5CI9t6yKqccx0jMEnHidaZEFdTK4 UNXl2Y/lVT6k5DEjxmYeW34wDj4uQKV8IortKyv9BvbnsW7m+kz0lQ5JYakf7X9jGwTH DpBYMNMtI8bnTx7sPbhBnyKJtRTSBASGNryagfghe93hoRW8Fb2f33ucBrJ2Dc1KDeXF hHk2s4BBGf4uxDAn4VzhsJYzWGSs8mcC7vjPnViBsxJG2wboGc734HzTRxxXMwkPXmPQ cBjQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1740476888; x=1741081688; h=user-agent:content-disposition:content-transfer-encoding :mime-version:message-id:reply-to:references:subject :list-unsubscribe:list-id:auto-submitted:cc:to:date:from :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=BNmCwX4fn4XtzbC1Drc08TBjvFTBySBf31V4g3wrOcI=; b=BdupdXG9oQ1B2sBlyE3c04WoMTxH53M8gkdHR3kb38WEjvdK8VrJE/xyHZvjOmwAvB +cyhTPTe1ZtT23zM5bkhQXYPkr/zkeJ4zuMOxQ1BGuDjI0ITdkv3YjV2HUe+OV0rNCDN x9NWlPNuoSPuv0F209YYpbbmbvhjn2oDO8vCVSqvTIHZqdIhmJx7OUx0ipiUjtKziNsf k4YC8eV3mLrBrOsSUIQ7P4F7tup1xEl7v2HP7JnydY1L0w8wzmhpBtjggX1xf3qFYCgt UHIA9Xx5hBHIoJQ+8lYsr4CSYEE0KwSb7eegSFDloKpxqYEHEJAwwK365kJjM+hl+4jJ Qz4A== X-Gm-Message-State: AOJu0YzKGN6Kd021OEYcdMLYWDE7aRv4XWTWJ6sEpDowG3DYu4rdFWoA HcSmimbcMuvGciC06JFCy6RozCOAfPR1WPc289rSfg5se9MAtBhHItHYTL9pt+vcpu6EcXrpibD P X-Gm-Gg: ASbGncvNElOMMldgi5xHsbz6UxZ0w49zaa3X1cFehlPXY5nf4KtpQ5jMNfuEZz1onYH 5gF1mb4PVYp67+cd5L9Y6p6RnBPf5oa2Q8dmXnTnZ8QFF+G/ovW1ssRfcR4gWhtDEE+67I7wivT uKanydsVQlLQ7ScVZYe8n0s9S9CjbMbeJgrgMBnZPZtONtDS2uAWmJ4hKnk9e27Ul5+spp8+sCl r5Lo0pIpl01kidOGd4IUid2nrXlB4/O0crynEcyf6m4CN/J90vu3gvosCxIoBRBxmXqUcMN356C t12fy9raaFFybhWE72vIbDk8s7S+tbCMJHpaPhjLciTaf7ybmlMTz3pcbQTbkmp5WcyL9uRnoI1 qAIJ+Kx8OVSbUyem5ig== X-Received: by 2002:a05:6000:47:b0:38c:617c:ee2f with SMTP id ffacd0b85a97d-38f6e95f4bdmr11089227f8f.13.1740476887989; Tue, 25 Feb 2025 01:48:07 -0800 (PST) Received: from gerrit.openvpn.in (ec2-18-159-0-78.eu-central-1.compute.amazonaws.com. [18.159.0.78]) by smtp.gmail.com with ESMTPSA id ffacd0b85a97d-390cd8fcfc6sm1693227f8f.94.2025.02.25.01.48.07 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 25 Feb 2025 01:48:07 -0800 (PST) From: "mrbff (Code Review)" X-Google-Original-From: "mrbff (Code Review)" X-Gerrit-PatchSet: 1 Date: Tue, 25 Feb 2025 09:48:06 +0000 To: plaisthos , flichtenheld Auto-Submitted: auto-generated X-Gerrit-MessageType: newchange X-Gerrit-Change-Id: Ic7b486ccb85df7fc1d6a573ac1315d235728822c X-Gerrit-Change-Number: 901 X-Gerrit-Project: openvpn X-Gerrit-ChangeURL: X-Gerrit-Commit: f693d2ac7b0823f5d0cd488dd2b49fcf0e1afe52 References: Message-ID: <59b9f9a5fbf15b28541a27925a75d25abd90da63-HTML@gerrit.openvpn.net> MIME-Version: 1.0 User-Agent: Gerrit/3.8.2 X-Spam-Score: -0.2 (/) X-Spam-Report: Spam detection software, running on the system "util-spamd-2.v13.lw.sourceforge.com", has NOT identified this incoming email as spam. The original message has been attached to this so you can view it or label similar future email. If you have any questions, see the administrator of that system for details. Content preview: Attention is currently required from: flichtenheld, plaisthos. Hello plaisthos, flichtenheld, I'd like you to do a code review. Please visit Content analysis details: (-0.2 points, 6.0 required) pts rule name description ---- ---------------------- -------------------------------------------------- -0.0 RCVD_IN_DNSWL_NONE RBL: Sender listed at https://www.dnswl.org/, no trust [209.85.221.41 listed in list.dnswl.org] 0.0 RCVD_IN_VALIDITY_SAFE_BLOCKED RBL: ADMINISTRATOR NOTICE: The query to Validity was blocked. See https://knowledge.validity.com/hc/en-us/articles/20961730681243 for more information. [209.85.221.41 listed in sa-trusted.bondedsender.org] 0.0 RCVD_IN_VALIDITY_RPBL_BLOCKED RBL: ADMINISTRATOR NOTICE: The query to Validity was blocked. See https://knowledge.validity.com/hc/en-us/articles/20961730681243 for more information. [209.85.221.41 listed in bl.score.senderscore.com] 0.0 RCVD_IN_MSPIKE_H2 RBL: Average reputation (+2) [209.85.221.41 listed in wl.mailspike.net] 0.0 SPF_HELO_NONE SPF: HELO does not publish an SPF Record -0.0 SPF_PASS SPF: sender matches SPF record 0.0 WEIRD_PORT URI: Uses non-standard port number for HTTP 0.0 HTML_MESSAGE BODY: HTML included in message 0.1 DKIM_SIGNED Message has a DKIM or DK signature, not necessarily valid -0.1 DKIM_VALID_AU Message has a valid DKIM or DK signature from author's domain -0.1 DKIM_VALID Message has at least one valid DKIM or DK signature -0.1 DKIM_VALID_EF Message has a valid DKIM or DK signature from envelope-from domain 0.0 T_KAM_HTML_FONT_INVALID Test for Invalidly Named or Formatted Colors in HTML X-Headers-End: 1tmrY3-0008CS-Nd Subject: [Openvpn-devel] [M] Change in openvpn[master]: redirect-gateway: add route toward new remote host when using persist... X-BeenThere: openvpn-devel@lists.sourceforge.net X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Reply-To: marco@mandelbit.com, arne-openvpn@rfc2549.org, openvpn-devel@lists.sourceforge.net, frank@lichtenheld.com Cc: openvpn-devel Errors-To: openvpn-devel-bounces@lists.sourceforge.net X-getmail-retrieved-from-mailbox: Inbox X-GMAIL-THRID: =?utf-8?q?1825022318973553583?= X-GMAIL-MSGID: =?utf-8?q?1825022318973553583?= X-getmail-filter-classifier: gerrit message type newchange Attention is currently required from: flichtenheld, plaisthos. Hello plaisthos, flichtenheld, I'd like you to do a code review. Please visit http://gerrit.openvpn.net/c/openvpn/+/901?usp=email to review the following change. Change subject: redirect-gateway: add route toward new remote host when using persist-tun ...................................................................... redirect-gateway: add route toward new remote host when using persist-tun When both --redirect-gateway and --persist-tun are used together, a route must be added for each new remote host we attempt to connect to. Change-Id: Ic7b486ccb85df7fc1d6a573ac1315d235728822c Signed-off-by: Marco Baffo --- M src/openvpn/init.c M src/openvpn/route.c M src/openvpn/route.h 3 files changed, 188 insertions(+), 22 deletions(-) git pull ssh://gerrit.openvpn.net:29418/openvpn refs/changes/01/901/1 diff --git a/src/openvpn/init.c b/src/openvpn/init.c index b57e5f8..63b7bbf 100644 --- a/src/openvpn/init.c +++ b/src/openvpn/init.c @@ -2184,6 +2184,10 @@ "route-pre-down", c->c2.es); + if (c->mode == CM_P2P && c->options.persist_tun) + { + del_route_towards_remote(c); + } delete_routes(c->c1.route_list, c->c1.route_ipv6_list, c->c1.tuntap, ROUTE_OPTION_FLAGS(&c->options), c->c2.es, &c->net_ctx); @@ -2245,6 +2249,11 @@ c->c2.es); } + if (c->mode == CM_P2P && c->options.persist_tun) + { + del_route_towards_remote(c); + } + del_wfp_block(c, adapter_index); } gc_free(&gc); @@ -4825,6 +4834,17 @@ } } + /** + * When using both --redirect-gateway and --persist-tun, + * if the connection to the server is lost, a /32 (or /128 if IPv6) route must be added + * to ensure connectivity to the next remote. + */ + if (c->mode == CM_P2P + && c->options.persist_tun) + { + add_route_towards_remote(c); + } + /* * Actually do UID/GID downgrade, and chroot, if requested. * May be delayed by --client, --pull, or --up-delay. diff --git a/src/openvpn/route.c b/src/openvpn/route.c index bc41492..1e4deb5 100644 --- a/src/openvpn/route.c +++ b/src/openvpn/route.c @@ -43,6 +43,7 @@ #include "options.h" #include "networking.h" #include "integer.h" +#include "openvpn.h" #include "memdbg.h" @@ -884,30 +885,14 @@ } /* add VPN server host route if needed */ - if (need_remote_ipv6_route) + if (need_remote_ipv6_route + && !(rl6->iflags & RL_DID_LOCAL)) { if ( (rl6->rgi6.flags & (RGI_ADDR_DEFINED|RGI_IFACE_DEFINED) ) == (RGI_ADDR_DEFINED|RGI_IFACE_DEFINED) ) { - struct route_ipv6 *r6; - ALLOC_OBJ_CLEAR_GC(r6, struct route_ipv6, &rl6->gc); - - r6->network = *remote_host_ipv6; - r6->netbits = 128; - if (!(rl6->rgi6.flags & RGI_ON_LINK) ) - { - r6->gateway = rl6->rgi6.gateway.addr_ipv6; - } - r6->metric = 1; -#ifdef _WIN32 - r6->adapter_index = rl6->rgi6.adapter_index; -#else - r6->iface = rl6->rgi6.iface; -#endif - r6->flags = RT_DEFINED | RT_METRIC_DEFINED; - - r6->next = rl6->routes_ipv6; - rl6->routes_ipv6 = r6; + rl6->routes_ipv6 = create_host_route_ipv6(*remote_host_ipv6, rl6); + rl6->iflags |= RL_DID_LOCAL; } else { @@ -919,6 +904,30 @@ return ret; } +struct route_ipv6 * +create_host_route_ipv6(struct in6_addr remote_host_ipv6, struct route_ipv6_list *rl6) +{ + struct route_ipv6 *r6; + ALLOC_OBJ_CLEAR_GC(r6, struct route_ipv6, &rl6->gc); + + r6->network = remote_host_ipv6; + r6->netbits = 128; + if (!(rl6->rgi6.flags & RGI_ON_LINK) ) + { + r6->gateway = rl6->rgi6.gateway.addr_ipv6; + } + r6->metric = 1; +#ifdef _WIN32 + r6->adapter_index = rl6->rgi6.adapter_index; +#else + r6->iface = rl6->rgi6.iface; +#endif + r6->flags = RT_DEFINED | RT_METRIC_DEFINED; + r6->next = rl6->routes_ipv6; + + return r6; +} + static bool add_route3(in_addr_t network, in_addr_t netmask, @@ -1055,7 +1064,8 @@ /* if remote_host is not ipv4 (ie: ipv6), just skip * adding this special /32 route */ if ((rl->spec.flags & RTSA_REMOTE_HOST) - && rl->spec.remote_host != IPV4_INVALID_ADDR) + && rl->spec.remote_host != IPV4_INVALID_ADDR + && !(rl->iflags & RL_DID_LOCAL)) { ret = add_route3(rl->spec.remote_host, IPV4_NETMASK_HOST, rl->rgi.gateway.addr, tt, flags | ROUTE_REF_GW, @@ -1282,7 +1292,7 @@ { delete_route_ipv6(r6, tt, flags, es, ctx); } - rl6->iflags &= ~RL_ROUTES_ADDED; + rl6->iflags &= ~(RL_ROUTES_ADDED | RL_DID_LOCAL); } if (rl6) @@ -1291,6 +1301,131 @@ } } +void +add_route_towards_remote(struct context *c) +{ + ASSERT(c->c1.link_socket_addrs); + + int current_remote_family = c->c1.link_socket_addrs[0].actual.dest.addr.sa.sa_family; + + if (current_remote_family == AF_INET && c->c1.route_list + && (c->c1.route_list->flags & RG_REROUTE_GW)) + { + if (c->c1.route_list->iflags & RL_DID_LOCAL) + { + del_route_towards_remote(c); + } + + in_addr_t current_remote = ntohl(c->c1.link_socket_addrs[0].actual.dest.addr.in4.sin_addr.s_addr); + + if (add_route3(current_remote, + IPV4_NETMASK_HOST, + c->c1.route_list->rgi.gateway.addr, + c->c1.tuntap, + ROUTE_OPTION_FLAGS(&c->options) | ROUTE_REF_GW, + &c->c1.route_list->rgi, + c->c2.es, + &c->net_ctx)) + { + c->c1.route_list->iflags |= RL_DID_LOCAL; + c->c1.route_list->spec.remote_host = current_remote; + } + } + else if (current_remote_family == AF_INET6 && c->c1.route_ipv6_list + && (c->c1.route_ipv6_list->flags & RG_REROUTE_GW)) + { + if (c->c1.route_ipv6_list->iflags & RL_DID_LOCAL) + { + del_route_towards_remote(c); + } + + const struct in6_addr *remote_host_ipv6 = &(c->c1.link_socket_addrs[0].actual.dest.addr.in6.sin6_addr); + struct route_ipv6_list *rl6 = c->c1.route_ipv6_list; + + if ((rl6->rgi6.flags & (RGI_ADDR_DEFINED|RGI_IFACE_DEFINED)) == + (RGI_ADDR_DEFINED|RGI_IFACE_DEFINED)) + { + struct route_ipv6 *r6 = create_host_route_ipv6(*remote_host_ipv6, rl6); + + if (add_route_ipv6(r6, c->c1.tuntap, + ROUTE_OPTION_FLAGS(&c->options), c->c2.es, &c->net_ctx)) + { + rl6->routes_ipv6 = r6; + rl6->iflags |= RL_DID_LOCAL; + } + } + else + { + msg(M_WARN, "ROUTE6: IPv6 route overlaps with IPv6 remote address, but could not determine IPv6 gateway address + interface, expect failure\n" ); + } + } +} + +void +del_route_towards_remote(struct context *c) +{ + /* If the function is called from do_close_tun() it means that the socket + * has already been closed and c->c2.link_sockets[0]->info.lsa` used in + * `add_route_towards_remote()` cleaned up. So we should use + * `c->c1.link_socket_addrs[0]` instead. + */ + ASSERT(c->c1.link_socket_addrs); + + int current_remote_family = 0; + + if (c->c1.link_socket_addrs[0].actual.dest.addr.sa.sa_family) + { + current_remote_family = c->c1.link_socket_addrs[0].actual.dest.addr.sa.sa_family; + } + else if (c->c1.link_socket_addrs[0].current_remote) + { + current_remote_family = c->c1.link_socket_addrs[0].current_remote->ai_family; + } + + if (current_remote_family == AF_INET && c->c1.route_list + && (c->c1.route_list->flags & RG_REROUTE_GW) + && (c->c1.route_list->iflags & RL_DID_LOCAL)) + { + del_route3(c->c1.route_list->spec.remote_host, + IPV4_NETMASK_HOST, + c->c1.route_list->rgi.gateway.addr, + c->c1.tuntap, + ROUTE_OPTION_FLAGS(&c->options) | ROUTE_REF_GW, + &c->c1.route_list->rgi, + c->c2.es, + &c->net_ctx); + c->c1.route_list->iflags &= ~RL_DID_LOCAL; + } + else if (current_remote_family == AF_INET6 && c->c1.route_ipv6_list + && (c->c1.route_ipv6_list->flags & RG_REROUTE_GW) + && (c->c1.route_ipv6_list->iflags & RL_DID_LOCAL)) + { + struct in6_addr *remote_host_ipv6 = &c->c1.route_ipv6_list->remote_host_ipv6; + struct route_ipv6 *host_route = create_host_route_ipv6(*remote_host_ipv6, c->c1.route_ipv6_list); + + for (struct route_ipv6 *prev = NULL, *r6 = c->c1.route_ipv6_list->routes_ipv6; r6; r6 = r6->next) + { + if (memcmp(&r6->network, &host_route->network, sizeof(struct in6_addr)) + || r6->netbits != host_route->netbits + || memcmp(&r6->gateway, &host_route->gateway, sizeof(struct in6_addr))) + { + continue; + } + + delete_route_ipv6(r6, c->c1.tuntap, ROUTE_OPTION_FLAGS(&c->options), c->c2.es, &c->net_ctx); + if (!prev) + { + c->c1.route_ipv6_list->routes_ipv6 = r6->next; + } + else + { + prev->next = r6->next; + } + c->c1.route_ipv6_list->iflags &= ~RL_DID_LOCAL; + } + } +} + #ifndef ENABLE_SMALL static const char * diff --git a/src/openvpn/route.h b/src/openvpn/route.h index 98ea79e..b1b23f9 100644 --- a/src/openvpn/route.h +++ b/src/openvpn/route.h @@ -286,6 +286,14 @@ const struct route_gateway_info *rgi, const struct env_set *es, openvpn_net_ctx_t *ctx); +/* Function to add a route towards the new remote when using + * `--redirect-gateway` and `--persist-tun` options together. */ +void add_route_towards_remote(struct context *c); + +/* Function to delete the route towards the remote when using + * `--redirect-gateway` and `--persist-tun` options together. */ +void del_route_towards_remote(struct context *c); + void add_route_to_option_list(struct route_option_list *l, const char *network, const char *netmask, @@ -353,6 +361,9 @@ const struct route_gateway_info *rgi, const struct route_ipv6_gateway_info *rgi6); +/* Return a `route_ipv6 *` /128 IPv6 route toward the remote host */ +struct route_ipv6 *create_host_route_ipv6(struct in6_addr remote_host_ipv6, struct route_ipv6_list *rl6); + /* * Test if addr is reachable via a local interface (return ILA_LOCAL), * or if it needs to be routed via the default gateway (return