mirror of
https://gitlab.freedesktop.org/NetworkManager/NetworkManager.git
synced 2026-02-05 19:20:35 +01:00
core/platform: preserve external and static route metrics
Two issues: 1) routes added by external programs or by users with /sbin/ip should not be modified, but NetworkManager was always changing those routes' metrics to match the device priority. This caused the nm_platform_ipX_route_sync() functions to remove the original, external route (due to mismatched metric) and re-add the route with the NetworkManager specified metric. Fix that by not touching routes which came from the kernel. 2) Static routes (from persistent connections) that specified a metric were getting their metric overwritten with the NetworkManager device priority. Stop doing that. Since the platform no longer defaults the metric to 1024, callers of nm_platform_ip4_route_add() (like NMPolicy's default route handling) must do that themselves, if they desire this behavior.
This commit is contained in:
parent
067db6f8d7
commit
4c16f3c7e2
5 changed files with 24 additions and 20 deletions
|
|
@ -265,7 +265,6 @@ nm_ip4_config_commit (const NMIP4Config *config, int ifindex, int priority)
|
|||
|
||||
for (i = 0; i < count; i++) {
|
||||
memcpy (&route, nm_ip4_config_get_route (config, i), sizeof (route));
|
||||
route.metric = priority;
|
||||
|
||||
/* Don't add the route if it's more specific than one of the subnets
|
||||
* the device already has an IP address on.
|
||||
|
|
@ -279,6 +278,11 @@ nm_ip4_config_commit (const NMIP4Config *config, int ifindex, int priority)
|
|||
if (nm_ip4_config_get_never_default (config) && route.network == 0)
|
||||
continue;
|
||||
|
||||
/* Use the default metric only if the route was created by NM and
|
||||
* didn't already specify a metric.
|
||||
*/
|
||||
if (route.source != NM_PLATFORM_SOURCE_KERNEL && !route.metric)
|
||||
route.metric = priority ? priority : NM_PLATFORM_ROUTE_METRIC_DEFAULT;
|
||||
g_array_append_val (routes, route);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -266,7 +266,6 @@ nm_ip6_config_commit (const NMIP6Config *config, int ifindex, int priority)
|
|||
|
||||
for (i = 0; i < count; i++) {
|
||||
memcpy (&route, nm_ip6_config_get_route (config, i), sizeof (route));
|
||||
route.metric = priority;
|
||||
|
||||
/* Don't add the route if it's more specific than one of the subnets
|
||||
* the device already has an IP address on.
|
||||
|
|
@ -280,6 +279,11 @@ nm_ip6_config_commit (const NMIP6Config *config, int ifindex, int priority)
|
|||
if (nm_ip6_config_get_never_default (config) && IN6_IS_ADDR_UNSPECIFIED (&route.network))
|
||||
continue;
|
||||
|
||||
/* Use the default metric only if the route was created by NM and
|
||||
* didn't already specify a metric.
|
||||
*/
|
||||
if (route.source != NM_PLATFORM_SOURCE_KERNEL && !route.metric)
|
||||
route.metric = priority ? priority : NM_PLATFORM_ROUTE_METRIC_DEFAULT;
|
||||
g_array_append_val (routes, route);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -659,9 +659,9 @@ update_ip4_routing (NMPolicy *policy, gboolean force_update)
|
|||
if (ip_ifindex <= 0)
|
||||
ip_ifindex = parent_ifindex;
|
||||
|
||||
if (!nm_platform_ip4_route_add (ip_ifindex, 0, 0, int_gw, 0, mss)) {
|
||||
(void) nm_platform_ip4_route_add (parent_ifindex, gw_addr, 32, 0, 0, parent_mss);
|
||||
if (!nm_platform_ip4_route_add (ip_ifindex, 0, 0, int_gw, 0, mss))
|
||||
if (!nm_platform_ip4_route_add (ip_ifindex, 0, 0, int_gw, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss)) {
|
||||
(void) nm_platform_ip4_route_add (parent_ifindex, gw_addr, 32, 0, NM_PLATFORM_ROUTE_METRIC_DEFAULT, parent_mss);
|
||||
if (!nm_platform_ip4_route_add (ip_ifindex, 0, 0, int_gw, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss))
|
||||
nm_log_err (LOGD_IP4 | LOGD_VPN, "Failed to set default route.");
|
||||
}
|
||||
|
||||
|
|
@ -670,9 +670,9 @@ update_ip4_routing (NMPolicy *policy, gboolean force_update)
|
|||
int mss = nm_ip4_config_get_mss (ip4_config);
|
||||
|
||||
g_assert (ip_iface);
|
||||
if (!nm_platform_ip4_route_add (ip_ifindex, 0, 0, gw_addr, 0, mss)) {
|
||||
(void) nm_platform_ip4_route_add (ip_ifindex, gw_addr, 32, 0, 0, mss);
|
||||
if (!nm_platform_ip4_route_add (ip_ifindex, 0, 0, gw_addr, 0, mss)) {
|
||||
if (!nm_platform_ip4_route_add (ip_ifindex, 0, 0, gw_addr, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss)) {
|
||||
(void) nm_platform_ip4_route_add (ip_ifindex, gw_addr, 32, 0, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss);
|
||||
if (!nm_platform_ip4_route_add (ip_ifindex, 0, 0, gw_addr, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss)) {
|
||||
nm_log_err (LOGD_IP4, "Failed to set default route.");
|
||||
}
|
||||
}
|
||||
|
|
@ -853,9 +853,9 @@ update_ip6_routing (NMPolicy *policy, gboolean force_update)
|
|||
if (ip_ifindex <= 0)
|
||||
ip_ifindex = parent_ifindex;
|
||||
|
||||
if (!nm_platform_ip6_route_add (ip_ifindex, in6addr_any, 0, *int_gw, 0, mss)) {
|
||||
(void) nm_platform_ip6_route_add (parent_ifindex, *gw_addr, 128, in6addr_any, 0, parent_mss);
|
||||
if (!nm_platform_ip6_route_add (ip_ifindex, in6addr_any, 0, *int_gw, 0, mss)) {
|
||||
if (!nm_platform_ip6_route_add (ip_ifindex, in6addr_any, 0, *int_gw, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss)) {
|
||||
(void) nm_platform_ip6_route_add (parent_ifindex, *gw_addr, 128, in6addr_any, NM_PLATFORM_ROUTE_METRIC_DEFAULT, parent_mss);
|
||||
if (!nm_platform_ip6_route_add (ip_ifindex, in6addr_any, 0, *int_gw, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss)) {
|
||||
nm_log_err (LOGD_IP6 | LOGD_VPN, "Failed to set default route.");
|
||||
}
|
||||
}
|
||||
|
|
@ -864,9 +864,9 @@ update_ip6_routing (NMPolicy *policy, gboolean force_update)
|
|||
} else {
|
||||
int mss = nm_ip6_config_get_mss (ip6_config);
|
||||
|
||||
if (!nm_platform_ip6_route_add (ip_ifindex, in6addr_any, 0, *gw_addr, 0, mss)) {
|
||||
(void) nm_platform_ip6_route_add (ip_ifindex, *gw_addr, 128, in6addr_any, 0, mss);
|
||||
if (!nm_platform_ip6_route_add (ip_ifindex, in6addr_any, 0, *gw_addr, 0, mss))
|
||||
if (!nm_platform_ip6_route_add (ip_ifindex, in6addr_any, 0, *gw_addr, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss)) {
|
||||
(void) nm_platform_ip6_route_add (ip_ifindex, *gw_addr, 128, in6addr_any, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss);
|
||||
if (!nm_platform_ip6_route_add (ip_ifindex, in6addr_any, 0, *gw_addr, NM_PLATFORM_ROUTE_METRIC_DEFAULT, mss))
|
||||
nm_log_err (LOGD_IP6, "Failed to set default route.");
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1478,9 +1478,6 @@ nm_platform_ip4_route_add (int ifindex,
|
|||
g_return_val_if_fail (mss >= 0, FALSE);
|
||||
g_return_val_if_fail (klass->ip4_route_add, FALSE);
|
||||
|
||||
if (!metric)
|
||||
metric = 1024;
|
||||
|
||||
return klass->ip4_route_add (platform, ifindex, network, plen, gateway, metric, mss);
|
||||
}
|
||||
|
||||
|
|
@ -1494,9 +1491,6 @@ nm_platform_ip6_route_add (int ifindex,
|
|||
g_return_val_if_fail (mss >= 0, FALSE);
|
||||
g_return_val_if_fail (klass->ip6_route_add, FALSE);
|
||||
|
||||
if (!metric)
|
||||
metric = 1024;
|
||||
|
||||
return klass->ip6_route_add (platform, ifindex, network, plen, gateway, metric, mss);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -156,6 +156,8 @@ typedef struct {
|
|||
guint flags; /* ifa_flags from <linux/if_addr.h>, field type "unsigned int" is as used in rtnl_addr_get_flags. */
|
||||
} NMPlatformIP6Address;
|
||||
|
||||
#define NM_PLATFORM_ROUTE_METRIC_DEFAULT 1024
|
||||
|
||||
typedef struct {
|
||||
int ifindex;
|
||||
NMPlatformSource source;
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue