Fetch the repository succeeded.
This action will force synchronization from src-openEuler/systemd, which will overwrite any changes that you have made since you forked the repository, and can not be recovered!!!
Synchronous operation will process in the background and will refresh the page when finishing processing. Please be patient.
From 2bd5bbbd39d5c825ed520e8282840b76b8f7fc79 Mon Sep 17 00:00:00 2001
From: Yu Watanabe <watanabe.yu+github@gmail.com>
Date: Sat, 21 Aug 2021 03:51:39 +0900
Subject: [PATCH] network: fix logic for checking gateway address is ready
This fixes the followings:
- The corresponding route or address to the gateway address must be in
the same link.
- IPv6 link local address is not necessary to be reachable.
Fixes an issue reported in https://github.com/systemd/systemd/issues/8686#issuecomment-902562324.
(cherry picked from commit 3333350a0e1917395d3654731ca985ea668bca9b)
Conflict:NA
Reference:https://github.com/systemd/systemd/commit/2bd5bbbd39d5c825ed520e8282840b76b8f7fc79
---
src/network/networkd-nexthop.c | 7 +---
src/network/networkd-route.c | 72 ++++++++++++++++++++--------------
src/network/networkd-route.h | 2 +-
3 files changed, 44 insertions(+), 37 deletions(-)
diff --git a/src/network/networkd-nexthop.c b/src/network/networkd-nexthop.c
index a52e5dcb16..c5cba88f46 100644
--- a/src/network/networkd-nexthop.c
+++ b/src/network/networkd-nexthop.c
@@ -791,12 +791,7 @@ static bool nexthop_is_ready_to_configure(Link *link, const NextHop *nexthop) {
}
}
- if (nexthop->onlink <= 0 &&
- in_addr_is_set(nexthop->family, &nexthop->gw) &&
- !manager_address_is_reachable(link->manager, nexthop->family, &nexthop->gw))
- return false;
-
- return true;
+ return gateway_is_ready(link, nexthop->onlink, nexthop->family, &nexthop->gw);
}
int request_process_nexthop(Request *req) {
diff --git a/src/network/networkd-route.c b/src/network/networkd-route.c
index 068915616e..b7852f6eec 100644
--- a/src/network/networkd-route.c
+++ b/src/network/networkd-route.c
@@ -753,6 +753,8 @@ static bool prefix_route_address_is_reachable(const Address *a, int family, cons
if (a->family != family)
return false;
+ if (!address_is_ready(a))
+ return false;
if (FLAGS_SET(a->flags, IFA_F_NOPREFIXROUTE))
return false;
if (in_addr_is_set(a->family, &a->in_addr_peer))
@@ -766,37 +768,34 @@ static bool prefix_route_address_is_reachable(const Address *a, int family, cons
FAMILY_ADDRESS_SIZE(family) * 8) > 0;
}
-bool manager_address_is_reachable(Manager *manager, int family, const union in_addr_union *address) {
- Link *link;
+static bool link_address_is_reachable(Link *link, int family, const union in_addr_union *address) {
+ Route *route;
- assert(manager);
+ assert(link);
+ assert(link->manager);
assert(IN_SET(family, AF_INET, AF_INET6));
assert(address);
- HASHMAP_FOREACH(link, manager->links_by_index) {
- Route *route;
- SET_FOREACH(route, link->routes)
- if (route_address_is_reachable(route, family, address))
- return true;
- SET_FOREACH(route, link->routes_foreign)
- if (route_address_is_reachable(route, family, address))
- return true;
- }
+ SET_FOREACH(route, link->routes)
+ if (route_address_is_reachable(route, family, address))
+ return true;
+ SET_FOREACH(route, link->routes_foreign)
+ if (route_address_is_reachable(route, family, address))
+ return true;
/* If we do not manage foreign routes, then there may exist a prefix route we do not know,
* which was created on configuring an address. Hence, also check the addresses. */
- if (!manager->manage_foreign_routes)
- HASHMAP_FOREACH(link, manager->links_by_index) {
- Address *a;
-
- SET_FOREACH(a, link->addresses)
- if (prefix_route_address_is_reachable(a, family, address))
- return true;
- SET_FOREACH(a, link->addresses_foreign)
- if (prefix_route_address_is_reachable(a, family, address))
- return true;
- }
+ if (!link->manager->manage_foreign_routes) {
+ Address *a;
+
+ SET_FOREACH(a, link->addresses)
+ if (prefix_route_address_is_reachable(a, family, address))
+ return true;
+ SET_FOREACH(a, link->addresses_foreign)
+ if (prefix_route_address_is_reachable(a, family, address))
+ return true;
+ }
return false;
}
@@ -1692,6 +1691,22 @@ int link_request_static_routes(Link *link, bool only_ipv4) {
return 0;
}
+bool gateway_is_ready(Link *link, int onlink, int family, const union in_addr_union *gw) {
+ assert(link);
+ assert(gw);
+
+ if (onlink > 0)
+ return true;
+
+ if (!in_addr_is_set(family, gw))
+ return true;
+
+ if (family == AF_INET6 && in6_addr_is_link_local(&gw->in6))
+ return true;
+
+ return link_address_is_reachable(link, family, gw);
+}
+
static int route_is_ready_to_configure(const Route *route, Link *link) {
MultipathRoute *m;
NextHop *nh = NULL;
@@ -1735,19 +1750,13 @@ static int route_is_ready_to_configure(const Route *route, Link *link) {
return r;
}
- if (route->gateway_onlink <= 0 &&
- in_addr_is_set(route->gw_family, &route->gw) > 0 &&
- !manager_address_is_reachable(link->manager, route->gw_family, &route->gw))
+ if (!gateway_is_ready(link, route->gateway_onlink, route->gw_family, &route->gw))
return false;
ORDERED_SET_FOREACH(m, route->multipath_routes) {
union in_addr_union a = m->gateway.address;
Link *l = NULL;
- if (route->gateway_onlink <= 0 &&
- !manager_address_is_reachable(link->manager, m->gateway.family, &a))
- return false;
-
if (m->ifname) {
if (link_get_by_name(link->manager, m->ifname, &l) < 0)
return false;
@@ -1759,6 +1768,9 @@ static int route_is_ready_to_configure(const Route *route, Link *link) {
}
if (l && !link_is_ready_to_configure(l, true))
return false;
+
+ if (!gateway_is_ready(l ?: link, route->gateway_onlink, m->gateway.family, &a))
+ return false;
}
return true;
diff --git a/src/network/networkd-route.h b/src/network/networkd-route.h
index 2d262819ad..235a91f08d 100644
--- a/src/network/networkd-route.h
+++ b/src/network/networkd-route.h
@@ -78,8 +78,8 @@ int route_configure_handler_internal(sd_netlink *rtnl, sd_netlink_message *m, Li
int route_remove(const Route *route, Manager *manager, Link *link);
int link_has_route(Link *link, const Route *route);
-bool manager_address_is_reachable(Manager *manager, int family, const union in_addr_union *address);
int manager_find_uplink(Manager *m, int family, Link *exclude, Link **ret);
+bool gateway_is_ready(Link *link, int onlink, int family, const union in_addr_union *gw);
int link_drop_routes(Link *link);
int link_drop_foreign_routes(Link *link);
--
2.33.0
此处可能存在不合适展示的内容,页面不予展示。您可通过相关编辑功能自查并修改。
如您确认内容无涉及 不当用语 / 纯广告导流 / 暴力 / 低俗色情 / 侵权 / 盗版 / 虚假 / 无价值内容或违法国家有关法律法规的内容,可点击提交进行申诉,我们将尽快为您处理。